Are virtualization machanism acting at the operating system level.
They can execute multiple and isolated Linux systems on the same machine (host) but they use the kernel of the host.
Containers are different from virtual machines that virtualize the full OS (the kernel) and, usually, even the hardware.
Allows the developers to have an environment that is reproducible and the same as the production environment.
Build: tools for creating containarized applications. The application is packaged together with dependencies and infrastructure. The result is a docker image.
Ship: an image shared on a docker registry (e.g. https://hub.docker.com)
Run: A docker container is a runtime running a representation of a docker image.
Docker host: a machine running the "docker engine"
Docker client: program configured to talk with the engine.
The host checks whether the requested image is already chached on the machine, if not, it downloads from the central repository.
When a client runs a container, a new container is created running the specified image. Several containers can run the same image (analogy container/image ~ program/process).
Containers are executed on the docker host and the standard output is (eventually) redirected to the client.
A "docker image" is a read-only template. Containers are read-write.
An image consists of several layer (using union filesystem) combined into a single image file.
When an image is changed a new layer is built on top of the previous one. Only the new layer is eventually distributed.
Common layers are reused by several images
Modifications in a running container are not saved.
A container should run a single command/service.
The following are the core commands for the docker
client.
$ docker images
Show installed images in the system with few informations
$ docker search <name>
Search on Docker Hub images with the specifed name. The search result shows:
Automated build
As soon as a commit is pushed on the corresponding git repository, the image is automatically rebuilt on Docker Hub
$ docker history <image>
Prints an image layers hystory.
$ docker rmi <name>
Removes a downloaded image from the computer
$ docker pull <name>:<tag>
Downloads (if not already pulled) the image with given name and tag. If no tag is specified then it assumest the "latest".
Comman layers already downloaded are not downloaded again.
$ docker run <name>
Runs the specified image in a container.
Option | Purpose |
---|---|
-i | Keep stdin open even if not attached |
-t | Allocate a pseudo-tty |
-d | Run container in background and print container ID |
--name | Assign a name to the container |
--rm | Automatically remove the container when it exits |
-e | Set environment variable |
-P | Publish all exposed ports to random ports on the host |
-p | Publish a container's port(s) to the specified host port |
-m | Limit the memory |
The first time the images is downloaded (i.e. all its layers).
$ docker run hello-world
View running containers
$ docker ps [-a]
The -a
option shows also terminated containers.
An exited container that keeps stdin active (e.g. ubuntu) can be restarted by specifying its container name. Once restarted you have to reattach to the container.
Get container name from the NAMES column: docker ps -a
$ docker stop <name>
$ docker restart <name>
$ docker attach <name>
Remove a stopped container from the containers list (ps -a
)
$ docker rm <name>
A special directory used by one or several containers.
Volumes are initialized when a container is created and they survive when containers are deleted.
$ docker run --name myvol -v /dir ubuntu
Creates a container with name "myvol" with a volume in the directory dir
.
$ docker run -it --rm --volumes-from myvol ubuntu /bin/bash
Executes the ununtu bash in a container using the volumes of the container "myvol". What's written in the directory "/adirectory" will be persisted in the volume of the container "myvolume".
Executing several containers with the above commands to share files. The files are persistent as long as the container "myvol" is not removed.
$ docker inspect myvolume
Returns a JSON description of the volume. The interesting part is "Source", telling the absolute path in our computer where the contents of the volume is stored. The source is under the "Mounts subtree.
-v <host-dir>:<container-dir>
If the local directory does not exist it will be created with root privileges.
To restart a docker container when it crashes itself, use the restart policies provided by Docker itself.
$ docker run --restart always <image-name>
-p <local-port>:<container-port>
If the container exposes "container-port", this will be visible from the host at port "local-port".
Text file with instructions to create and build images according to the Dockerfile syntax.
For example what the used would run from the command line in a container,
such as apt
commands to install packages, creation of config files.
The build
command uses thi sfile and executes the instructions to create
an image.
At build time you pass a "context" that is used for creating the image:
In the Dockerfile you can access only the directories of the context (at build time). The context directory is processed recursively.
All its contents are sent to the Docker host for the build.
Use a .dockerignore
to exclude paths and thus increment build performance.
The paths in the Dockerfile are meant relative to the context ("/" is the root of the context).
Never specify "/" as the context you pass to the build! All your harddisk contents would be sent to the Docker host.
FROM
First noncomment instruction in the Dockerfile. Specifies the Docker image to start from. All the following instructions are executed on the base image.
Example
FROM ubuntu
The command creates a "chain" of images with installed software (docker history <image>
).
COPY
Copy moultiple source files from the context to the filesys of the container a the specified path
COPY .vimrc /home
ENV
Sets the environment variable
ENV HOSTNAME=test
RUN
Executes a command
RUN apt-get update
CMD
Commnad that is executed by default in a container from the image. If specified multiple times only the last CMD will be considered
CMD ["/bin/echo","hello world"]
Can be overridden from the command line if you specify a command after the
image name in the docker run
command (e.g. ubuntu /bin/bash).
EXPOSE
Informs the network ports that the container will listen on
EXPOSE 8093
Given the following Dockerfile
FROM python
CMD ["python","--version"]
Enter the folder where the Dockerfile is stored.
$ docker build -t hello-python .
The name of the image to create is specified with -t
option.
The directory for the context is .
(current directory).
Social network to share docker images.
Login
$ docker login
To push an image
$ docker push <user-id>/<image-name>
Compose is a tool for defining and running multi-container Docker applications. A YAML file is used to configure the application's services.
A single command is then used to create and start all the services defined in the configuration file.
Start services set on the background:
$ docker-compose up -d
Stop services set:
$ docker-compose down
Inspect and follow the started services log:
$ docker-compose logs -f
Inspect the services volumes:
$ docker-compose volumes
For more informations about compose refer to the official documentation here.
To find dependent child images of a given image:
$ docker inspect \
--format='{{.Id}} {{.Parent}}' \
$(docker images --filter since=<PARENT-ID> --quiet) \
| grep <PARENT-ID>
Remove unused volumes:
$ docker system prune --volumes
Remove all unused images and volumes:
$ docker system prune --all
To change the default (/var/lib/docker
) docker root directory the beste way is
to create/edit the
config.json
file in /etc/docker/config.json
.
In particular it should contain the following entry:
{
data-root: <FOLDER-PATH>
}
Proudly self-hosted on a cheap Raspberry Pi