Heard about it before, but really had to start using it in WATonomous.

Docker is a containerization platform (container management service). It allows for easy deployment of software in a loosely isolated sandbox (containers). The key benefit of Docker is that it allows users to package an application with all of its dependencies into a standardized unit.

Does Docker operate at the application layer?

Not only at application layer, it utilizates the kernel features for containerization.

This is what happens in WATonomous

If you are running more than one container, you can let your containers communicate with each other by attaching them to the same network. Docker creates virtual networks which let your containers talk to each other. In a network, a container has an IP address, and optionally a hostname.

There’s Docker Hub, where we have the official docker container images.

  • Building an image = recreating the steps needed by docker build or docker compose build
  • Running an image = bringing it up, either docker run or docker compose up

Don't confused Docker with Virtual Machine

Docker images are much smaller than VMs. Docker only virtualize the application layer, but VMs virtualize both the application and OS Kernel layer.

docker run -d -it --mount type=bind,source="$(pwd)",target=/app  ubuntu:22.04

Force a x86 distro in a M1 Mac?

You can do something like this:

docker run --platform linux/amd64  osrf/ros:galactic-desktop

What is the difference between docker and a VM?

  • A VM does full hardware virtualization, and run its own OS. On the other hand, Docker shares the host’s OS Kernel.

So when would would ever want a VM over Docker?

It’s relevant when it comes to security, and you want true full-isolation, avoiding any cross contaminiation. If a container exploits kernel vulnerabilities, it could affect the host or other containers.

An example

A containerized application exploits a shared kernel vulnerability to gain unauthorized access to host resources. Other containers could be compromised.

  • VM Solution: A VM, with its own full OS and kernel, isolates environments completely. Even if one VM is compromised, others remain unaffected.
  • In production, both VMs and Docker are used. VMs for full isolation, and Docker for scalability


I didn’t even know this wtf, there’s nvidia-docker for docker with GPU.


I wanted to download the docker images on another disk

sudo dockerd --debug


  • Docker Images: An image is a combination of a file system and parameters. It is the blueprint of the thing that actually will get build, we use a Dockerfile to create these blueprints. docker compose allows us to bring up multiple containers up using multiple images.
  • Docker Containers: Instances of Docker images. These are the actual building.

Images don’t run. Containers run.

Committing and Pushing to docker

docker commit <existing-container> <hub-user>/<repo-name>[:<tag>]
 docker push <hub-user>/<repo-name>:<tag>

Main Commands


List all Docker images

docker images

List all Docker containers

docker ps [FLAGS]


  • -a: Show all containers, running and stopped
  • -s: Display total file size
Start up a Docker Container

Start up a Docker Container from an image

docker run <ImageID>
  • -d: start container in a detached mode
  • -p: Publish a container’s port(s) to the host, very important for port binding
  • --name: Assign name to container
  • -it: Combination of both —interactive(-i) and —tty(-t): keep STDIN open even if not attached, and allocate a pseudo-TTY
  • -v: Bind mount a volume
  • --rm: Automatically remove the container when it exits
  • --net/--network: Connect a container to a network

Note: If it can’t find the image locally, it runs docker pull first.

You can also up a container through its container id

docker start <ContainerID>
docker stop <ContainerID>
docker logs

To enter a container (its interactive shell), run

docker exec -it <ContainerID>  /bin/bash

To exit, just write exit, or CTRL + D


Remove container

docker rm <ContainerID>

Remove images

docker rmi <ImageID>

Docker Compose

We can map a command into a structured file.

docker-compose -f docker-compose.yml up

“up” starts all the containers in the .yml file


A Dockerfile is a blueprint for creating Docker Images.

To build from a Dockerfile, run

docker build -t TAG_NAME .


  • -f: Name of the Dockerfile, default is ‘PATH/Dockerfile’
  • -force-rm: Always remove intermediate containers
  • -no-cache: Do not use cache when building the image
Dockerfile Syntax

The Dockerfile has to start with the FROM argument, which specifies the base Docker Image.

The RUN instruction has 2 forms:

  • RUN <command> (shell form, the command is run in a shell. Default is /bin/sh -c on linux, or cmd /S /C on Windows)
  • RUN [“executable”, “param1”, “param2”] (exec form)

The CMD instruction has 3 forms:

  • CMD [“executable”, “param1”, “param2”] (exec form, this is the preferred form)
  • CMD [“param1”, “param2”] (As default parameters to ENTRYPOINT
  • CMD command param1 param2 (shell form)

IMPORTANT: There can only be one CMD instruction in a Dockerfile.

Example Dockerfile

FROM osrf/ros:foxy-desktop
SHELL ["/bin/bash", "-c"]
# dependencies
RUN apt-get update --fix-missing && \
    apt-get install -y git \
                       nano \
                       vim \
                       python3-pip \


To mount, add this to the docker compose file:

	- ./models:/models

Docker Networks