Docker is a tool designed to make it easier to create, deploy, and run applications by using containers. Containers allow a developer to package up an application with all of the parts it needs, such as libraries and other dependencies, and ship it all out as one package. By doing so, thanks to the container, the developer can rest assured that the application will run on any other Linux machine regardless of any customized settings that machine might have that could differ from the machine used for writing and testing the code.

In a way, Docker is a bit like a virtual machine. But unlike a virtual machine, rather than creating a whole virtual operating system, Docker allows applications to use the same Linux kernel as the system that they're running on and only requires applications be shipped with things not already running on the host computer. This gives a significant performance boost and reduces the size of the application.

1 Install docker

Docker is available in two editions: Community Edition (CE) and Enterprise Edition (EE).

Docker Community Edition (CE) is ideal for developers and small teams looking to get started with Docker and experimenting with container-based apps. Docker CE has two update channels, stable and edge:

  • Stable gives you reliable updates every quarter
  • Edge gives you new features every month

2 Hello world

Docker containers are run from Docker images. By default, it pulls these images from Docker Hub, a Docker registry managed by Docker, the company behind the Docker project. Anybody can build and host their Docker images on Docker Hub, so most applications and Linux distributions you'll need to run Docker containers have images that are hosted on Docker Hub.

To check whether you can access and download images from Docker Hub, type:

Copy
$ docker run hello-world
Unable to find image 'hello-world:latest' locally
latest: Pulling from library/hello-world
5b0f327be733: Pull complete 
Digest: sha256:1f19634d26995c320618d94e6f29c09c6589d5df3c063287a00e6de8458f8242
Status: Downloaded newer image for hello-world:latest

Hello from Docker!
This message shows that your installation appears to be working correctly.
...

2.1 What happened ?

Though the above pic is self explanatory, we’ll just discuss the basics / CLI commands for working with docker containers.

2.1.1 Create container

Create a container to run it later on with required image.

Copy
$ docker create --name <container-name> <image-name>

2.1.2 Run docker container

Run the docker container with the required image and specified command / process. ‘-d’ flag is used for running the container in background.

Copy
docker run -it -d --name <container-name> <image-name> bash

2.1.3 Pause container

Used to pause the processes running inside the container.

Copy
$ docker pause <container-id/name>

2.1.4 Unpause container

Used to unpause the processes inside the container.

Copy
$ docker unpause <container-id/name>

2.1.5 Start container

Start the container, if present in stopped state.

Copy
$ docker start <container-id/name>

2.1.6 Stop container

To stop the container and processes running inside the container:

Copy
$ docker stop <container-id/name>

To stop all the running docker containers

Copy
$ docker stop $(docker ps -a -q)

2.1.7 Restart container

It is used to restart the container as well as processes running inside the container.

Copy
$ docker restart <container-id/name>

2.1.8 Kill container

We can kill the running container.

Copy
$ docker kill <container-id/name>

2.1.9 Destroy container

Its preferred to destroy container, only if present in stopped state instead of forcefully destroying the running container.

Copy
$ docker rm <container-id/name>

To remove all the stopped docker containers

Copy
$ docker rm $(docker ps -q -f status=exited)

3 Working with images

3.1 Search images

You can search for images available on Docker Hub by using the docker command with the search subcommand. For example, to search for the CentOS image, type:

Copy
docker search centos
NAME                               DESCRIPTION                                     STARS     OFFICIAL   AUTOMATED
centos                             The official build of CentOS.                   3631      [OK]       
ansible/centos7-ansible            Ansible on Centos7                              101                  [OK]
jdeathe/centos-ssh                 CentOS-6 6.9 x86_64 / CentOS-7 7.3.1611 x8...   83                   [OK]
tutum/centos                       Simple CentOS docker image with SSH access      33                   
imagine10255/centos6-lnmp-php56    centos6-lnmp-php56                              30                   [OK]
gluster/gluster-centos             Official GlusterFS Image [ CentOS-7 +  Glu...   20                   [OK]
kinogmt/centos-ssh                 CentOS with SSH                                 17                   [OK]
centos/php-56-centos7              Platform for building and running PHP 5.6 ...   9                    
openshift/base-centos7             A Centos7 derived base image for Source-To...   7                    
openshift/mysql-55-centos7         DEPRECATED: A Centos7 based MySQL v5.5 ima...   6                    
centos/python-35-centos7           Platform for building and running Python 3...   6                    
darksheer/centos                   Base Centos Image -- Updated hourly             3                    [OK]
openshift/ruby-20-centos7          DEPRECATED: A Centos7 based Ruby v2.0 imag...   3                    
openshift/jenkins-2-centos7        A Centos7 based Jenkins v2.x image for use...   3                    
openshift/jenkins-1-centos7        DEPRECATED: A Centos7 based Jenkins v1.x i...   3                    
blacklabelops/centos               CentOS Base Image! Built and Updates Daily!     1                    [OK]
openshift/php-55-centos7           DEPRECATED: A Centos7 based PHP v5.5 image...   1                    
...

In the OFFICIAL column, OK indicates an image built and supported by the company behind the project. Once you've identifed the image that you would like to use, you can download it to your computer using the pull subcommand, like so:

Copy
$ docker pull centos
latest: Pulling from library/centos
d9aaf4d82f24: Pull complete 
Digest: sha256:eba772bac22c86d7d6e72421b4700c3f894ab6e35475a34014ff8de74c10872e
Status: Downloaded newer image for centos:latest

3.2 List available images

To see the images that have been downloaded to your computer, type:

Copy
$ docker images
REPOSITORY                    TAG                 IMAGE ID            CREATED             SIZE
centos                        latest              196e0ce0c9fb        2 days ago          197MB
hello-world                   latest              05a3bd381fc2        4 days ago          1.84kB

After an image has been downloaded, you may then run a container using the downloaded image with the run subcommand. If an image has not been downloaded when docker is executed with the run subcommand, the Docker client will first download the image.

3.3 Running a Docker Container

Let's run a container using the latest image of CentOS. The combination of the -i and -t switches gives you interactive shell access into the container:

Copy
$ docker run -it centos
[root@032022c1e4fc /]#

Your command prompt should change to reflect the fact that you're now working inside the container and should take this form:

[root@032022c1e4fc /]#     

Where 032022c1e4fc is the container id.

When you execute a command against an image you basically obtain a container. After the command that is executing into container ends, the container stops (you get a non-running or exited container). If you run another command into the same image again a new container is created and so on.

All the containers created will remain on the host filesystem until you choose to delete them by using the docker rm command.

In order to create and run a container, you need to run a command into a downloaded image, in this case centos, so a basic command would be to display the distribution version file inside the container using cat command, as in the following example:

Copy
$ docker run centos df -k
Filesystem     1K-blocks    Used Available Use% Mounted on
overlay         65792556 3542852  58877928   6% /
tmpfs            1023516       0   1023516   0% /dev
tmpfs            1023516       0   1023516   0% /sys/fs/cgroup
/dev/sda1       65792556 3542852  58877928   6% /etc/hosts
shm                65536       0     65536   0% /dev/shm
tmpfs            1023516       0   1023516   0% /sys/firmware

To run one of the containers again with the command that was executed to create it, first you must get the container ID (or the name automatically generated by Docker) by issuing the below command, which displays a list of the running and stopped (non-running) containers:

Copy
$ docker ps -l
CONTAINER ID        IMAGE               COMMAND             CREATED              STATUS                          PORTS               NAMES
1e1441ce8edc        centos              "df -k"             About a minute ago   Exited (0) About a minute ago                       suspicious_albattani

Once the container ID has been obtained, you can start the container again with the command that was used to create it, by issuing the following command:

Copy
$ docker start 1e1441ce8edc

A more elegant alternative so you don’t have to remember the container ID would be to allocate a unique name for every container you create by using the --name option on command line, as in the following example:

Copy
$ docker run --name luna centos df -k

Now, remember that if you run commands against an image, a new container is created with an id. And if you don't name the image, a random name will be given. To see all container images created type (you will see all containers created from previous commands):

Copy
$ docker ps -a
CONTAINER ID        IMAGE                                COMMAND                  CREATED             STATUS                      PORTS                                                                                              NAMES
399d3d3d5fc1        centos                               "df -k"                  7 seconds ago       Exited (0) 6 seconds ago                                                                                                       luna
263e5e31677a        centos                               "df -k"                  31 seconds ago      Exited (0) 31 seconds ago                                                                                                      frosty_wright
6759e599c362        centos                               "/bin/bash"              45 seconds ago      Exited (0) 42 seconds ago                                                                                                      priceless_lewin
3e751982c09b        hello-world                          "/hello"                 5 hours ago         Exited (0) 5 hours ago                                                                                                         elegant_nobel

To remove containers we can use rm command:

Copy
$ docker rm 399d3d3d5fc1 263e5e31677a 6759e599c362

3.4 Keep docker container running

As we see after the command that is executing into container ends, the container stops (you get a non-running or exited container). How can we keep the container running ? We can use the -i command to set

Copy
$ docker run --name mars -i -d centos
54de064e3923df5b4d2eb0ce79c6f04b293a7bacefda2830b1d8f583bcb0575a
Copy
$ docker ps
CONTAINER ID        IMAGE                                COMMAND                  CREATED             STATUS              PORTS                                                                                              NAMES
54de064e3923        centos                               "/bin/bash"              3 seconds ago       Up 2 seconds                                                                                                           mars

We have container nammed mars (54de064e3923) running. To connect to container simply type:

Copy
$ docker exec -it mars /bin/bash
[root@54de064e3923 /]#

To exit the container, simply type exit. And to stop the container type:

Copy
$ docker stop mars

As container is stopped if you try to exec a command (connect via bash) to it you will get:

Copy
$ docker exec -it mars /bin/bash
Error response from daemon: Container 56bc38bafba43c22214de3ee6e78594be66ce38b9f1f865dce4142bbcd927839 is not running

To start container again, simply type:

Copy
$ docker start mars

3.5 Start a docker container as daemon process

Instead of running docker container with an interactive shell it is also possible to let docker container to run as a daemon which means that the docker container would run in the background completely detached from your current shell.

The following CentOS docker container will start as a daemonized container using -d option, while at the same time executing ping 8.8.8.8 using an endless bash while loop.

Copy
$ docker run --name centos -d centos /bin/sh -c "while true; do ping 8.8.8.8; done"

Using docker's ps command we see the that our centos container is running:

Copy
$ docker ps
CONTAINER ID        IMAGE                                COMMAND                  CREATED             STATUS              PORTS                                                                                              NAMES
0210648d8980        centos                               "/bin/sh -c 'while..."   5 seconds ago       Up 4 seconds                                                                                                           centos

The actual output from the above endless while loop can be access by examining container logs:

Copy
$ docker logs 0210648d8980
64 bytes from 8.8.8.8: icmp_seq=146 ttl=37 time=0.314 ms
64 bytes from 8.8.8.8: icmp_seq=147 ttl=37 time=0.309 ms
64 bytes from 8.8.8.8: icmp_seq=148 ttl=37 time=0.315 ms
64 bytes from 8.8.8.8: icmp_seq=149 ttl=37 time=0.227 ms
...

Use docker exec to reattach to your container interactive shell:

Copy
$ docker exec -it centos /bin/bash
[root@0210648d8980 /]#

Examine running processes in container to see ps is efectively running.

Copy
[root@0210648d8980 /]# ps -el
F S   UID   PID  PPID  C PRI  NI ADDR SZ WCHAN  TTY          TIME CMD
4 S     0     1     0  0  80   0 -  2911 -      ?        00:00:00 sh
4 S     0     5     1  0  80   0 -  6204 -      ?        00:00:00 ping
4 S     0     6     0  0  80   0 -  2946 -      pts/0    00:00:00 bash
0 R     0    21     6  0  80   0 - 11333 -      pts/0    00:00:00 ps

Furthermore, using docker exec we can also run any desired command within the docker container.

Copy
$ docker exec -it centos ls -l
total 64
-rw-r--r--   1 root root 15836 Sep 11 15:53 anaconda-post.log
lrwxrwxrwx   1 root root     7 Sep 11 15:51 bin -> usr/bin
drwxr-xr-x   5 root root   340 Sep 17 09:47 dev
drwxr-xr-x   1 root root  4096 Sep 17 09:34 etc
drwxr-xr-x   2 root root  4096 Nov  5  2016 home
lrwxrwxrwx   1 root root     7 Sep 11 15:51 lib -> usr/lib
lrwxrwxrwx   1 root root     9 Sep 11 15:51 lib64 -> usr/lib64
drwx------   2 root root  4096 Sep 11 15:51 lost+found
drwxr-xr-x   2 root root  4096 Nov  5  2016 media
...

3.6 Stop a docker container

To stop a docker container use it's ID.

Copy
$ docker stop 0210648d8980

3.7 Configure a docker image

TO DO

This section is incomplete and will be concluded as soon as possible.

3.8 Committing Changes in a Container to a Docker Image

When you start up a Docker image, you can create, modify, and delete files just like you can with a virtual machine. The changes that you make will only apply to that container. You can start and stop it, but once you destroy it with the docker rm command, the changes will be lost for good.

3.9 Pushing Docker Images to a Docker Repository

TO DO

This section is incomplete and will be concluded as soon as possible.

4 Application data

In general, Docker containers are ephemeral, running just as long as it takes for the command issued in the container to complete. Sometimes, however, applications need to share access to data or persist data after a container is deleted. Databases, user-generated content for a web site and log files are just a few examples of data that is impractical or impossible to include in a Docker image but which applications need to access.

So even is possible to store data within the writable layer of a container, there are some downsides:

  • The data won’t persist when that container is no longer running, and it can be difficult to get the data out of the container if another process needs it.
  • A container’s writable layer is tightly coupled to the host machine where the container is running. You can’t easily move the data somewhere else.
  • Writing into a container’s writable layer requires a storage driver to manage the filesystem. The storage driver provides a union filesystem, using the Linux kernel. This extra abstraction reduces performance as compared to using data volumes, which write directly to the host filesystem.
Docker offers three different ways to mount data into a container from the Docker host: volumes, bind mounts, or tmpfs volumes. When in doubt, volumes are almost always the right choice. Keep reading for more information about each mechanism for mounting data into containers.

4.1 Docker volumes

Volumes are the preferred mechanism for persisting data generated by and used by Docker containers. While bind mounts are dependent on the directory structure of the host machine, volumes are completely managed by Docker.

To see available volumes type:

Copy
$ docker volume ls
DRIVER              VOLUME NAME
local               5429ccd48cda667e9dabc173af13e32f5f37b1371d2ba228521067c7600da606

To see the structure of default volume shown before type:

Copy
docker volume inspect  5429ccd48cda667e9dabc173af13e32f5f37b1371d2ba228521067c7600da606
[
    {
        "Driver": "local",
        "Labels": null,
        "Mountpoint": "/var/lib/docker/volumes/5429ccd48cda667e9dabc173af13e32f5f37b1371d2ba228521067c7600da606/_data",
        "Name": "5429ccd48cda667e9dabc173af13e32f5f37b1371d2ba228521067c7600da606",
        "Options": {},
        "Scope": "local"
    }
]

Docker Volumes can be created and attached in the same command that creates a container, or they can be created independent of any containers and then attached later.

4.1.1 Creating an Independent Volume

The docker volume create command allows you to create a volume without relating it to any particular container. We'll use this command to add a volume named DataVolume1:

Copy
$ docker volume create --name DataVolume1
DataVolume1

To make use of the volume, we'll create a new container from the centos image, using the --rm flag to automatically delete it when we exit. We'll use -v to mount the new volume. -v requires the name of the volume, a colon, then the absolute path to where the volume should appear inside the container. If the directories in the path don't exist as part of the image, they'll be created when the command runs. If they do exist, the mounted volume will hide the existing content.

Copy
$ docker run -ti --rm -v DataVolume1:/datavolume1 centos

While we're there, we'll write some data to the volume:

Copy
[root@d286edc98bcd /]# echo "Example1" > /datavolume1/Example1.txt

Because we used the --rm flag, our container will be automatically deleted when we exit. Our volume, however, will still be accessible.

Copy
[root@d286edc98bcd /]# exit

We can verify the volume is present on the system with docker volume inspect:

Copy
$ docker volume inspect DataVolume1
[
    {
        "Driver": "local",
        "Labels": null,
        "Mountpoint": "/var/lib/docker/volumes/DataVolume1/_data",
        "Name": "DataVolume1",
        "Options": {},
        "Scope": "local"
    }
]

Next, let's start a new container and attach DataVolume1:

Copy
$ docker run -ti --rm -v DataVolume1:/datavolume1 centos
[root@d7376706e876 /]# cat /datavolume1/Example1.txt
Example1

We can even look at the data on the host at the path listed as the Mountpoint. We should avoid altering it, however, as it can cause data corruption if applications or containers are unaware of changes

On MacOS, /var/lib/docker/ does not exits and you need to get access of the linux virtual machine using docker.

Copy
$ sudo screen ~/Library/Containers/com.docker.docker/Data/com.docker.driver.amd64-linux/tty
$ / # cd /var/lib/docker/volumes
$ /var/lib/docker/volumes # ls -l
drwxr-xr-x    3 root     root          4096 Sep 17 08:17 5429ccd48cda667e9dabc173af13e32f5f37b1371d2ba228521067c7600da606
drwxr-xr-x    3 root     root          4096 Sep 17 15:17 DataVolume1
-rw-------    1 root     root         32768 Sep 17 15:17 metadata.db

4.1.2 Creating a Volume from an Existing Directory with Data

Generally, creating a volume independently with docker volume create and creating one while creating a container are equivalent, with one exception. If we create a volume at the same time as we create a container and we provide the path to a directory that contains data in the base image, that data will be copied into the volume.

As an example, we’ll create a container and add the data volume at /data/source, a directory which contains data in the base image:

Copy
$ docker run -ti --rm -v DataVolume3:/var centos

All the content from the base image's /var directory is copied into the volume, and we can mount that volume in a new container. This time, rather than relying on the base image's default bash command, we'll issue our own ls command, which will show the contents of the volume without entering the shell:

Copy
$ docker run --rm -v DataVolume3:/DataVolume3 centos ls DataVolume3
adm
cache
db
empty
games
gopher
kerberos
lib
local
lock
log
mail
nis
opt
preserve
run
spool
tmp

DataVolume3 has a copy of the contents of the base image's /var directory. You can verify it by typing:

Copy
$ ls -l /var/lib/docker/volumes/DataVolume3/_data

It's unlikely that we would want to mount /var/ in this way, but this can be helpful if we've crafted our own image and want an easy way to preserve data. In our next example, we'll demonstrate how a volume can be shared between multiple containers.

4.1.3 Sharing Data between Multiple Docker Containers

So far, we've attached a volume to one container at a time. But often, we'll want multiple containers to attach to the same data volume. This is relatively straightforward to accomplish, but there's one critical caveat: at this time, Docker doesn't handle file locking. If you need multiple containers writing to the volume, the applications running in those containers must be designed to write to shared data stores in order to prevent data corruption.

Create Container4 and DataVolume4

Use docker run to create a new container named Container4 with a data volume attached.

Copy
$ docker run -ti --name=Container4 -v DataVolume4:/datavolume4 centos

Next we'll create a file and add some text and exit:

Copy
[root@a59bb24d16bb /]# echo "This file is shared between containers" > /datavolume4/Example4.txt
[root@a59bb24d16bb /]# exit

Create Container5 and Mount Volumes from Container4

We're going to create Container5, and mount the volumes from Container4:

Copy
$ docker run -ti --name=Container5 --volumes-from Container4 ubuntu
[root@3cb8781aaca1 /]# cat /datavolume4/Example4.txt
This file is shared between containers

Now let's append some text from the second container:

Copy
[root@3cb8781aaca1 /]# echo "Both containers can write to DataVolume4" >> /datavolume4/Example4.txt
[root@3cb8781aaca1 /]# exit

Next, we'll check that our data is still present to Container4.

View Changes Made in Container5

Let's check for the changes that were written to the data volume by Container5 by restarting Container4:

Copy
$ docker start -ai Container4
[root@a59bb24d16bb /]# cat /datavolume4/Example4.txt
This file is shared between containers
Both containers can write to DataVolume4

Again, Docker doesn't handle any file locking, so applications must account for the file locking themselves. It is possible to mount a Docker volume as read-only to ensure that data corruption won't happen by accident when a container requires read-only access by adding :ro. Let's look at how this works.

Start Container 6 and Mount the Volume Read-Only

Once a volume has been mounted in a container, rather than unmounting it like we would with a typical Linux file system, we instead create a new container mounted the way we want it and, if needed, remove the previous container. To make the volume read-only, we append :ro to the end of the container name:

Copy
$ docker run -ti --name=Container6 --volumes-from Container4:ro centos
[root@6b39c97fe51c /]#

We'll check the read-only status by trying to remove our example file:

Copy
[root@6b39c97fe51c /]# rm /datavolume4/Example4.txt
rm: remove regular file '/datavolume4/Example4.txt'? y
rm: cannot remove '/datavolume4/Example4.txt': Read-only file system

Now that we’re done, let’s clean up our containers and volume:

Copy
$ docker rm Container4 Container5 Container6
$ docker volume rm DataVolume4

4.2 Bind mounts

TO DO

This section is incomplete and will be concluded as soon as possible.

4.3 tmpfs mounts

TO DO

This section is incomplete and will be concluded as soon as possible.

4.4 Storage drivers

TO DO

This section is incomplete and will be concluded as soon as possible.

5 Monitoring

5.1 Statistics (by container id)

Copy
$ docker stats
CONTAINER           CPU %               MEM USAGE / LIMIT       MEM %               NET I/O               BLOCK I/O             PIDS
40c8ef3581b0        0.25%               158.8 MiB / 58.92 GiB   0.26%               106.7 kB / 1.914 kB   179 MB / 61.69 MB     186
01f54276bd7d        0.16%               154.1 MiB / 58.92 GiB   0.26%               106.4 kB / 1.914 kB   240.8 MB / 61.05 MB   186
e4180c297673        0.23%               151.8 MiB / 58.92 GiB   0.25%               105.8 kB / 1.914 kB   163.8 MB / 14.48 MB   186
a82db379a21b        0.19%               151.5 MiB / 58.92 GiB   0.25%               105.2 kB / 1.914 kB   185.6 MB / 63.03 MB   186
2a4cd87c3ce2        0.15%               151.8 MiB / 58.92 GiB   0.25%               104.8 kB / 1.914 kB   251.3 MB / 64 MB      186
a486789891b6        0.19%               150.4 MiB / 58.92 GiB   0.25%               104.3 kB / 1.956 kB   199.5 MB / 114.9 MB   186
b54389ac2b03        0.30%               151.8 MiB / 58.92 GiB   0.25%               103.3 kB / 1.914 kB   238.4 MB / 61.88 MB   186
b699ae7f6b2f        0.18%               152 MiB / 58.92 GiB     0.25%               102.9 kB / 1.956 kB   191 MB / 64.12 MB     186
95366ccd0ebc        0.21%               154.1 MiB / 58.92 GiB   0.26%               101.9 kB / 1.914 kB   212 MB / 11.94 MB     186
5de714d0b965        0.15%               151.5 MiB / 58.92 GiB   0.25%               101.4 kB / 1.914 kB   224.8 MB / 13.05 MB   186
...

5.1.1 Statistics (by container name)

Copy
$ docker stats $(docker ps | awk '{if(NR>1) print $NF}')
CONTAINER           CPU %               MEM USAGE / LIMIT       MEM %               NET I/O               BLOCK I/O             PIDS
ifx990              0.14%               158.9 MiB / 58.92 GiB   0.26%               106.7 kB / 1.914 kB   179 MB / 61.69 MB     186
ifx980              0.21%               154.1 MiB / 58.92 GiB   0.26%               106.4 kB / 1.914 kB   240.8 MB / 61.05 MB   186
ifx970              0.14%               151.9 MiB / 58.92 GiB   0.25%               105.8 kB / 1.914 kB   163.8 MB / 14.48 MB   186
ifx960              0.13%               151.6 MiB / 58.92 GiB   0.25%               105.2 kB / 1.914 kB   185.6 MB / 63.03 MB   186
ifx950              --                  -- / --                 --                  -- / --               -- / --               --
ifx940              0.14%               150.5 MiB / 58.92 GiB   0.25%               104.3 kB / 1.956 kB   199.5 MB / 114.9 MB   186
ifx930              0.16%               151.8 MiB / 58.92 GiB   0.25%               103.3 kB / 1.914 kB   238.4 MB / 61.88 MB   186
ifx920              --                  -- / --                 --                  -- / --               -- / --               --
ifx910              0.17%               154.2 MiB / 58.92 GiB   0.26%               101.9 kB / 1.914 kB   212 MB / 11.94 MB     186
ifx900              --                  -- / --                 --                  -- / --               -- / --               --
ifx890              --                  -- / --                 --                  -- / --               -- / --               --
ifx880              0.14%               148.2 MiB / 58.92 GiB   0.25%               99.91 kB / 1.914 kB   185 MB / 63.98 MB     186
ifx870              --                  -- / --                 --                  -- / --               -- / --               --
ifx860              0.14%               152.7 MiB / 58.92 GiB   0.25%               98.69 kB / 1.914 kB   286.2 MB / 125.4 MB   186
ifx850              0.13%               152.5 MiB / 58.92 GiB   0.25%               97.84 kB / 1.914 kB   220.7 MB / 125.4 MB   186
..

6 Backup

To understand the Docker container backup and recovery process we first need to understand the difference between docker image and docker container. A docker image contains an operating system with possibly one or more prefigured applications. Whereas, a docker container is a running instance created from an image.

6.1 Docker container backup

When we need make a backup of a docker container we commit its current state and save it as a docker image.

Copy
# docker ps
CONTAINER ID        IMAGE               COMMAND             CREATED             STATUS              PORTS               NAMES
78727078a04b        debian:8            "/bin/bash"         13 seconds ago      Up 11 seconds                           container1

From the above output we see a running docker container named container1 with an ID 78727078a04b. We now use commit command to take a snapshot of its current running state:

Copy
# docker commit -p  78727078a04b  container1
e09f9ac65c8b3095927c14ca0594868f73831bde0800ce66415afeb91aea93cf

With do above command we have first paused a running container with -p option, made a commit to save the entire snapshot as a docker image with a name container1:

Copy
# docker images
REPOSITORY                      TAG                 IMAGE ID            CREATED             VIRTUAL SIZE
container1                      latest              e09f9ac65c8b        39 seconds ago      125.1 MB

Now we have a container backup saved as an image waiting to be redeployed again. If we wish to redeploy our container1 image on another docker host system we may push the image to some private docker repository:

Copy
# docker login
# docker push container1

or we can save it as a tar file and move it freely to any desired docker host system for a deployment:

Copy
# docker save -o ~/container1.tar container1
[root@localhost lubos]# ls -l ~/container1.tar
-rw-r--r--. 1 root root 131017216 Jun 14 20:31 /root/container1.tar

6.2 Docker container recovery

The above paragraphs explained how to backup a docker container. In this section we will discuss how recover from a docker backup.

In case that we have pushed our backed up docker container image to a private repository we can simply use docker run command to start a new instance from the container1 image. If we have transferred our container1.tar backup file to another docker host system we first need to load backed up tar file into a docker's local image repository:

Copy
# docker load -i /root/container1.tar

Confirm that the image was loaded with:

Copy
# docker images

Now we can use docker run command to start a new instance from the above loaded container1 image.