Frequently Asked Questions about Docker Containers
By: Luis Vivero Peña
Tags: Dockerfiles, Containers, Docker, Docker Image, DevOps

Docker alternative Frequently Asked Questions

In the last time I have been working with students of Linux, Containers, and DevOps. There are some questions that came up time to time, so I wanted to write an article about these questions, because it can be useful to people who’s starting with Docker.

Note: there is a good documentation in the official Docker’s website, here.

As I have been asked for other stuff, I decided to write the article anyway.

Now let’s go to business:

Q: Will I lost the changes I have done to a container if I stop it?

A: Nop, you won’t lost any changes, at least if you remove the container.

You can confirm this by yourself, by following these steps:

i.- Run a new container.

docker container run -itd — name ubuntu20 ubuntu:20.10

Unable to find image ‘ubuntu:20.10’ locally

20.10: Pulling from library/ubuntu

d8b994c44286: Pull complete

b0773f3f1417: Pull complete

5b20aefff2dc: Pull complete

Digest: sha256:df1f60ba9ce1d98c42a1a65bf55ca2c1b78f3c0cc1d79416b5b31f34470de755

Status: Downloaded newer image for ubuntu:20.10

12a7e074a3d9ad8686ece50f8a8768c2d0f0e92e11fa6c52d63c6f282c7addc7

That will get (if needed) the image, run a container in detached mode, and will provide a terminal for connecting to it.

ii.- Get into the container.

docker container exec -it ubuntu20 bash

iii.- Let’s create a directory and put a file into it.

root@12a7e074a3d9:/#

root@12a7e074a3d9:/# pwd

/

root@12a7e074a3d9:/# mkdir testdir

root@12a7e074a3d9:/# cd testdir/

root@12a7e074a3d9:/testdir# echo “Hi, I’m staying here” > hello

root@12a7e074a3d9:/testdir# cat hello

Hi, I’m staying here

iv.- Let’s quit the container.

exit

v.- Stop the container.

docker container stop ubuntu20

ubuntu20

Verify with “docker ps” if it’s stopped.

docker ps

CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES

vi.- Start the container.

docker start ubuntu20

ubuntu20

vii.- Let’s check if the file is still there.

docker container exec -it ubuntu20 cat testdir/hello

Hi, I’m staying here

Alternatively you can run the same command in step ii., and do “cat testdir/hello”.

Q: If I already created two or more containers, are they configured by default to be in the same network, so I can connect from one container to each other?

A: They will be in the same network, but you will be able to reach them (from another container) using the IP only.

Let’s run a CentOS8 container, to make connectivity tests with the Ubuntu18 container:

docker container run -itd — name centos8 centos:centos8

Unable to find image ‘centos:centos8’ locally

centos8: Pulling from library/centos

7a0437f04f83: Pull complete

Digest: sha256:5528e8b1b1719d34604c87e11dcd1c0a20bedf46e83b5632cdeac91b8c04efc1

Status: Downloaded newer image for centos:centos8

47ce7aa73cfc665b32f40974cc20d465359d5046873f0ce8f4c943a6161fcd70

Connect to the CentOS8 container and get the hostname

docker container exec -it centos8 bash

hostname

47ce7aa73cfc

So, the Docker container’s hostnames are a bit weird, just a string (it’s the same Container ID!).

Let’s see what is the associated IP.

From the Host:

You can do “docker inspect <container ID>” and then take a look to the “Networks” section, and then “IPAddress”. Or better, just run the following command:

docker inspect -f ‘{{.Name}} — {{.NetworkSettings.IPAddress }}’ $(docker ps -aq)

/ubuntu20–172.17.0.2

/centos8–172.17.0.4

/alpine — 172.17.0.3

So, let’s ping the IP, hostname and container id of CentOS8 container from the Ubuntu20 one:

Connect to the Ubuntu20 container

docker container exec -it ubuntu20 bash

root@1c66c3c3ecd2:/#

Let’s install “iputils-ping”.

apt-get update

apt-get install iputils-ping

ping 172.17.0.4

PING 172.17.0.4 (172.17.0.4) 56(84) bytes of data.

64 bytes from 172.17.0.4: icmp_seq=1 ttl=64 time=0.099 ms

64 bytes from 172.17.0.4: icmp_seq=2 ttl=64 time=0.155 ms

64 bytes from 172.17.0.4: icmp_seq=3 ttl=64 time=0.152 ms

^C

— — 172.17.0.4 ping statistics — -

3 packets transmitted, 3 received, 0% packet loss, time 2058ms

rtt min/avg/max/mdev = 0.099/0.135/0.155/0.025 ms

Yeah, it gets the container by it’s IP.

Let’s try using the hostname/Container ID

ping 47ce7aa73cfc

ping: 47ce7aa73cfc: Name or service not known

Nope.

Let’s try the Container’s name:

ping centos8

ping: centos8: Name or service not known

So, the names will be able to be solved if the containers are in the same bridge network!

Q: How do I reach a container using its name?

A: It’s easy, you just need to create a bridged network and then connect the containers to it.

Let’s do it!

i.- Create a bridged network.

docker network create net1

a551989ec80fb51d6b71d4490500ad6fb6a80850179cf0fddec3621a748adda4

Note: by default it will be created as bridged network.

ii.- Connect the containers to the network we just created.

docker network connect net1 ubuntu20

docker network connect net1 centos8

Now, if you do “docker inspect ubuntu20”, and “docker inspect centos8” -in different terminals for comparing them- and you go to the Networks section, then to the Net1 subsection, you will see that they have the same Gateway and different IPAddress. That’s expected for being in the same network.

iii.- Let’s confirm they can connect to each other by name and Container ID.

docker container exec -it ubuntu20 bash

root@12a7e074a3d9:/# ping centos8

PING centos8 (172.18.0.3) 56(84) bytes of data.

64 bytes from centos8.net1 (172.18.0.3): icmp_seq=1 ttl=64 time=0.309 ms

64 bytes from centos8.net1 (172.18.0.3): icmp_seq=2 ttl=64 time=0.132 ms

64 bytes from centos8.net1 (172.18.0.3): icmp_seq=3 ttl=64 time=0.156 ms

^C

— — centos8 ping statistics — -

3 packets transmitted, 3 received, 0% packet loss, time 2004ms

rtt min/avg/max/mdev = 0.132/0.199/0.309/0.078 ms

Yep :D

Now let’s try by Container ID:

root@12a7e074a3d9:/# ping 47ce7aa73cfc

PING 47ce7aa73cfc (172.18.0.3) 56(84) bytes of data.

64 bytes from centos8.net1 (172.18.0.3): icmp_seq=1 ttl=64 time=0.097 ms

64 bytes from centos8.net1 (172.18.0.3): icmp_seq=2 ttl=64 time=0.154 ms

64 bytes from centos8.net1 (172.18.0.3): icmp_seq=3 ttl=64 time=0.158 ms

^C

— — 47ce7aa73cfc ping statistics — -

3 packets transmitted, 3 received, 0% packet loss, time 2005ms

rtt min/avg/max/mdev = 0.097/0.136/0.158/0.027 ms

That also work!

You can try pinging the ubuntu20 container from the centos8 one.

Note: you can find more information about this topic in the Docker’s official documentation.

Q: Do I need to give permissions in the firewall inside the container, so the services can be accessed from outside of it?

A: Nop, it doesn’t work in the same way than physical or VM systems. The idea of having containers is that they are light, much lighter than normal OS’s and VMs. So, in the most of cases, the images won’t have any firewall installed and configured.

Q: So, how to I access a service that’s running into a container from the host, or from another host?

A: You need to “expose” the port, that’s the concept we manage here. And there are a couple of ways to do that, by using the “-p <port>” or “-P” parameters.

You can see more details about this in the official documentation:

Publish or expose port (-p, — expose)

and

Published ports

So, let’s run an httpd container and expose port 80 to 8080 in the host. You can follow the instructions found in the httpd Docker Official Images website.

i.- Create a Dockerfile.

FROM httpd:latest

COPY ./public-html/ /usr/local/apache2/htdocs/

So, we need a “public-html” directory with something in there:

mkdir public-html

echo “Hello world :D” > public-html/index.html

ii.- Build the image.

For this, you need to be in the same directory than the Dockerfile.

docker build -t my-apache2 .

Apples-MBP:httpd luiseduardo$ docker build -t my-apache2 .

Sending build context to Docker daemon 3.584kB

Step 1/2 : FROM httpd:latest

latest: Pulling from library/httpd

6ec7b7d162b2: Pull complete

17e233bac21e: Pull complete

130aad5bf43a: Pull complete

81d0a34533d4: Pull complete

da240d12a8a4: Pull complete

Digest: sha256:a3a2886ec250194804974932eaf4a4ba2b77c4e7d551ddb63b01068bf70f4120

Status: Downloaded newer image for httpd:latest

— -> dd85cdbb9987

Step 2/2 : COPY ./public-html/ /usr/local/apache2/htdocs/

— -> 3e3c44731668

Successfully built 3e3c44731668

Successfully tagged my-apache2:latest

Note 1: you can use your own tag (indicated by the -t parameter).

Note 2: don’t forget the dot at the end.

Let’s see the image we just created:

docker image ls

REPOSITORY TAG IMAGE ID CREATED SIZE

my-apache2 latest 3e3c44731668 38 seconds ago 138MB

httpd latest dd85cdbb9987 12 days ago 138MB

centos centos8 300e315adb2f 2 weeks ago 209MB

ubuntu 20.10 671495eee4d8 3 weeks ago 79.5MB

alpine latest d6e46aa2470d 2 months ago 5.57MB

hello-world latest bf756fb1ae65 11 months ago 13.3kB

Yeah, it’s there.

iii.- Now let’s run a container based on that image.

iv.- Run the container and publish the port.

docker container run -itd — name mywebsite -p 8080:80 my-apache2

1d96a1e2dc7c2a25334a0123a26ae8be6a266c0ab5258fbc5ff2817316324611

That command will publish port 80 in the container to port 8080 in the host.

iv.- Take a look to localhost port 8080 with a browser to confirm.

That’s all ;)