Docker [05]: Docker Daemon

The docker daemon is a part of the docker engine. The docker engine is composed of other components such as the containerd and runc (will get to that later).

Docker client

The docker client is responsible for taking the user commands and converting them into the appropriate payload that will be sent over to the docker daemon. The default docker client that is being used is the binary /usr/bin/docker that is added by default to the Linux machine when installing docker. This client is used in the shell as follows

docker pull ubuntu

Can we create our own Docker Client?

Yes, why not? But let's move to the next section where we discuss the Docker daemon. Then we can create a custom Docker client. ๐Ÿ˜ƒ

Docker Deamon

Do you Remember the dockerd process that we saw previously when making pstree command?

This is the docker daemon process. It is the server side of the docker that is waiting to receive the user's commands. By default, the Docker daemon listens for connections on a Unix socket to accept requests from local clients. It can also be configured to listen on HTTP and receive requests from the network.

Listening to Unix sockets

We can find the socket file that is being used by docker to receive requests from local clients using the shell in /var/run/docker.sock

ubuntu@ip-172-31-31-29:~$ sudo ls -l /var/run/ | grep docker.sock
srw-rw---- 1 root docker 0 Sep 24 11:50 docker.sock

As you may already know unix socket is used for inter-process communication. This means that we can only send requests to the docker daemon from the same host. Let's not use the default docker executable and try curl.

curl --unix-socket /var/run/docker.sock http://localhost/images/json
[
  {
    "Containers": -1,
    "Created": 1697049277,
    "Id": "sha256:676aedd4776fe4617839f2517c46c44e8da9091d1c81a01f315101df51a2097f",
    "Labels": null,
    "ParentId": "",
    "RepoDigests": [
      "debian@sha256:7d3e8810c96a6a278c218eb8e7f01efaec9d65f50c54aae37421dc3cbeba6535"
    ],
    "RepoTags": [
      "debian:latest"
    ],
    "SharedSize": -1,
    "Size": 116549154,
    "VirtualSize": 116549154
  },
  {
    "Containers": -1,
    "Created": 1695637028,
    "Id": "sha256:3565a89d9e81a4cb4cb2b0d947c7c11227a3f358dc216d19fc54bfd77cd5b542",
    "Labels": {
      "org.opencontainers.image.ref.name": "ubuntu",
      "org.opencontainers.image.version": "22.04"
    },
    "ParentId": "",
    "RepoDigests": [
      "ubuntu@sha256:9b8dec3bf938bc80fbe758d856e96fdfab5f56c39d44b0cff351e847bb1b01ea"
    ],
    "RepoTags": [
      "ubuntu:latest"
    ],
    "SharedSize": -1,
    "Size": 77823976,
    "VirtualSize": 77823976
  }
]

This is similar to docker images ls command. It shows the docker images that exist on my machine.

Listening on HTTP

To configure remote access to the docker daemon, we need to make it accessible through the network. For that, we will make it listen on HTTP. For that, we will be making edits to the file /etc/docker/daemon.json to make it listen to both the Unix socket and HTTP socket on port 2375

{
  "hosts": ["unix:///var/run/docker.sock", "tcp://127.0.0.1:2375"]
}

Once we change the content of that file we need to restart the docker daemon process by

sudo systemctl restart docker.service

Then we can start sending HTTP requests to the daemon

ubuntu@ip-172-31-31-29:~$ curl -X GET http://localhost:2375/images/json
[{"Containers":-1,"Created":1697049277,"Id":"sha256:676aedd4776fe4617839f2517c46c44e8da9091d1c81a01f315101df51a2097f","Labels":null,"ParentId":"","RepoDigests":["debian@sha256:7d3e8810c96a6a278c218eb8e7f01efaec9d65f50c54aae37421dc3cbeba6535"],"RepoTags":["debian:latest"],"SharedSize":-1,"Size":116549154,"VirtualSize":116549154},{"Containers":-1,"Created":1695637028,"Id":"sha256:3565a89d9e81a4cb4cb2b0d947c7c11227a3f358dc216d19fc54bfd77cd5b542","Labels":{"org.opencontainers.image.ref.name":"ubuntu","org.opencontainers.image.version":"22.04"},"ParentId":"","RepoDigests":["ubuntu@sha256:9b8dec3bf938bc80fbe758d856e96fdfab5f56c39d44b0cff351e847bb1b01ea"],"RepoTags":["ubuntu:latest"],"SharedSize":-1,"Size":77823976,"VirtualSize":77823976},{"Containers":-1,"Created":1691124780,"Id":"sha256:01f29b872827fa6f9aed0ea0b2ede53aea4ad9d66c7920e81a8db6d1fd9ab7f9","Labels":{"org.opencontainers.image.ref.name":"ubuntu","org.opencontainers.image.version":"22.04"},"ParentId":"","RepoDigests":["ubuntu@sha256:ec050c32e4a6085b423d36ecd025c0d3ff00c38ab93a3d71a460ff1c44fa6d77"],"RepoTags":[],"SharedSize":-1,"Size":77823376,"VirtualSize":77823376}]

One of the Drawbacks of this approach is that docker will be accessible through the network which will introduce some security challenges. One approach to handle this is to use HTTPS, but it is still exposed ๐Ÿฅธ

References

3
Subscribe to my newsletter

Read articles from Mohammed Shetaya directly inside your inbox. Subscribe to the newsletter, and don't miss out.

Written by

Mohammed Shetaya
Mohammed Shetaya

Another engineer who is working his way up