Run a Container
creates a container from an image and starts it. Flags go before the image name; anything after the image name replaces the image's default command.
| Command | What it does |
|---|---|
| Start a container in the foreground (Ctrl+C stops it) | |
| Start it detached, in the background | |
| Give it a name so you can refer to it later | |
| Publish container port 80 on host port 8080 | |
| Publish it on localhost only | |
| Interactive shell in a fresh container | |
| Same, and delete the container when it exits | |
| Mount a named volume at /data (created if missing) | |
| Bind mount the current directory into the container | |
| Read-only bind mount | |
| Set an environment variable | |
| Load variables from a file | |
| Restart on failure and at daemon start, unless you stopped it | |
| Attach to a user-defined network | |
| Share the host's network stack, no port mapping needed | |
| Run as a specific UID and GID | |
| Set the working directory, then run a command | |
| Cap memory and CPU | |
| Replace the image's entrypoint | |
| Pull and run a specific architecture (Apple Silicon) | |
| Check for a newer image before starting | |
| Create without starting ( later) |
A typical long-running service:
docker run -d --name web \
-p 8080:80 \
-v data:/data \
--restart unless-stopped \
nginxfails with when an old container with that name exists, stopped or not. Remove it first with ; see Error response from daemon for the other common variants. For multi-container apps, put all of this in a compose file instead: see the docker compose commands sheet or the Docker Compose generator.
List Containers
| Command | What it does |
|---|---|
| Running containers | |
| All containers, including stopped and exited ones | |
| IDs only, for feeding into other commands | |
| All IDs | |
| Include disk usage per container | |
| The most recently created container | |
| Only exited containers (, , also work) | |
| Filter by name (substring match) | |
| Containers started from an image | |
| Custom columns | |
| Custom columns with a header | |
| Same as ; the noun-verb form is the newer spelling |
and are the same command. Docker added the , , groupings in 2017 and kept the short forms as aliases, so use whichever you type faster.
Stop, Start and Restart
| Command | What it does |
|---|---|
| Send SIGTERM, then SIGKILL after 10 seconds | |
| Give it 30 seconds to shut down cleanly | |
| SIGKILL immediately | |
| Send a different signal (reload nginx, for example) | |
| Start a stopped container with its original settings | |
| Start and attach to it, interactive | |
| Stop then start | |
| / | Freeze and thaw every process in it |
| Stop every running container | |
| Rename a container | |
| Change the restart policy without recreating | |
| Change resource limits live | |
| Block until it exits, then print the exit code |
A container that stops on its own the moment it starts has a main process that exited; run to see why. One that goes over and over is the same problem under a restart policy; see Docker container keeps restarting.
Remove Containers
| Command | What it does |
|---|---|
| Remove a stopped container | |
| Stop and remove in one step | |
| Also remove its anonymous volumes (named volumes stay) | |
| Remove every stopped container (running ones error out) | |
| Remove every container, running or not | |
| Remove all stopped containers | |
| Only ones stopped more than a day ago |
Removing a container does not remove its image or its named volumes.
Exec Into a Container
| Command | What it does |
|---|---|
| Open a shell ( where the image has it) | |
| Bash shell, on Debian and Ubuntu based images | |
| Run one command and print the output | |
| Shell as root, in a container that runs as another user | |
| Run in a specific directory | |
| With an extra environment variable | |
| Run in the background and return | |
| Attach to the main process's terminal (Ctrl+P, Ctrl+Q detaches) |
needs a running container. To poke at a stopped one, copy files out with or start it with a different command: .
Logs
Docker captures whatever the container's main process writes to stdout and stderr. Files the app writes inside the container do not show up here.
| Command | What it does |
|---|---|
| Everything so far | |
| Follow, like (Ctrl+C stops following, not the container) | |
| Last 100 lines | |
| Last 100 lines, then keep following | |
| Prefix each line with a timestamp | |
| Only the last ten minutes | |
| Since a point in time ( also works) | |
| Search the log; stderr must be merged first | |
| Save it to a file | |
| Where Docker stores the raw JSON log on the host |
Logs grow without limit unless you cap them. In set with , or pass to .
Copy Files
works on running and stopped containers. Paths are on the container side.
| Command | What it does |
|---|---|
| Copy a file out of a container | |
| Copy a directory out | |
| Copy a file in | |
| Copy the contents of a directory in (note the ) | |
| Preserve ownership and permissions | |
| Follow a symlink instead of copying the link |
Files copied in are owned by root unless you use . For anything more than a one-off, use a bind mount or a volume instead.
Build Images
| Command | What it does |
|---|---|
| Build from the Dockerfile in the current directory and tag it | |
| Apply two tags | |
| Use a different Dockerfile | |
| Rebuild every layer | |
| Pass an | |
| Stop at a stage in a multi-stage Dockerfile | |
| Build for a specific architecture | |
| Full build output instead of the collapsed view | |
| List local images ( is the same) | |
| Untagged leftovers from earlier builds | |
| Add a tag, usually to point at a registry | |
| Layers and the instruction that made each one | |
| Export an image to a tarball | |
| Import one | |
| Turn a container's current filesystem into an image (debugging only) |
The build context is the at the end: everything in that directory is sent to the daemon, so add a with , and build output in it. Starting from scratch? The Dockerfile generator writes a sensible multi-stage file for common stacks.
Pull, Push and Login
| Command | What it does |
|---|---|
| Pull from Docker Hub | |
| Pull a specific tag | |
| Pull a specific architecture | |
| Pull from another registry | |
| Log in to Docker Hub (prompts for username and password or token) | |
| Log in to another registry | |
| Log in from a script without the token in your history | |
| Forget the credentials | |
| Push an image (tag it with the registry name first) | |
| Search Docker Hub from the terminal | |
| Digest of the image you actually have |
is only a tag, not a promise of the newest version: fetches whatever the publisher last tagged , and a running container does not update itself when you pull. Pull, then recreate the container.
Remove Images
| Command | What it does |
|---|---|
| Remove one tag; the layers go when no tag references them | |
| Remove several | |
| Force, even if a stopped container uses it | |
| Remove every image not in use by a container | |
| Remove untagged leftovers only | |
| Same as | |
| Remove dangling images | |
| Remove every image no container is using |
means exactly that: stop and remove the container, then works. means another image was built on top of it; remove the child first.
Clean Up
Docker never deletes anything on its own. Stopped containers, old images, build cache and orphaned volumes pile up until the disk is full.
| Command | What it does |
|---|---|
| How much space containers, images, volumes and build cache use | |
| Per item | |
| Remove all stopped containers | |
| Remove dangling (untagged) images | |
| Remove every image no container uses | |
| Remove unused anonymous volumes | |
| Remove every unused volume, named ones too | |
| Remove networks no container is attached to | |
| Clear the build cache ( for all of it) | |
| Stopped containers, unused networks, dangling images and build cache in one go | |
| Same, plus every unused image | |
| Same, plus every unused volume. This deletes data | |
| Only things older than three days |
removes every volume that no running container is using right now. A database container that happens to be stopped counts as "not using" its volume, and the data is gone with no undo. Stop and think before adding . If the disk is already full, see Docker no space left on device for the order to do things in.
Volumes
Named volumes are managed by Docker and live under . Bind mounts map a host path you choose.
| Command | What it does |
|---|---|
| List volumes | |
| Create a named volume | |
| Driver, mount point on the host, labels | |
| Just the host path | |
| Remove a volume (fails while a container uses it) | |
| Remove unused anonymous volumes | |
| Mount a named volume | |
| Bind mount a host directory, read-only | |
| Same thing in the longer syntax | |
| Named volume in syntax | |
| Mount everything another container has mounted | |
| Anonymous volume: survives restarts, removed by |
Bind mount paths must be absolute, which is why shows up so often. Back up a named volume with a throwaway container:
docker run --rm -v data:/data -v $(pwd):/backup alpine \
tar czf /backup/data.tar.gz -C /data .Restore it the same way with .
Networks
Containers on the same user-defined network reach each other by container name. The default network does not do name resolution, so create one.
| Command | What it does |
|---|---|
| List networks | |
| Create a bridge network with DNS between members | |
| Members, subnet, gateway | |
| Attach a running container | |
| Detach it | |
| Remove (must have no members) | |
| Remove all unused networks | |
| Start a container on the network | |
| No isolation: the container uses the host's ports directly | |
| No network at all | |
| Show published ports for a container | |
| Add an entry |
From inside a container, reaches the host machine on Docker Desktop; on Linux add .
Inspect and Stats
| Command | What it does |
|---|---|
| Everything Docker knows about a container, as JSON | |
| One field | |
| The container's IP on the default bridge | |
| IP on any network | |
| Volumes and bind mounts | |
| How many times the restart policy fired | |
| Environment variables it was started with | |
| Healthcheck result, if the image defines one | |
| Works on images, volumes and networks too | |
| Live CPU, memory, network and disk I/O for every container | |
| One snapshot and exit | |
| Only these containers | |
| Processes running inside a container | |
| Files changed since the container started | |
| Stream daemon events (starts, stops, dies, pulls) | |
| Daemon configuration, storage driver, number of containers | |
| Client and server versions |
output is Go template territory: takes and . Pipe the plain output into when the template gets hard to read.
Dockerfile Instructions
The essentials, in the order they usually appear. Each instruction that changes the filesystem (, , ) creates a layer, and Docker caches layers from the top down, so put the things that change least first.
| Instruction | Example | Notes |
|---|---|---|
| Base image; starts a stage for multi-stage builds | ||
| Sets the directory for the instructions that follow, creating it if needed | ||
| Copy files from the build context. Copy dependency manifests before source so installs cache | ||
| Like COPY but also extracts local tar archives and fetches URLs. Prefer COPY unless you need that | ||
| Run a command at build time. Chain with to keep one layer | ||
| Environment variable, at build time and in the running container | ||
| Build-time only variable, set with | ||
| Documents the port. Does not publish it; on does | ||
| Run as a non-root user from here on | ||
| Marks a path as a mount point; an anonymous volume is created if none is given | ||
| How Docker decides the container is healthy | ||
| The executable. Arguments on are appended to it | ||
| Default arguments (or the whole command if there is no ENTRYPOINT). Replaced by arguments on | ||
| Metadata |
Use the JSON array form () for and . The shell form () wraps the command in , so PID 1 is the shell and your process never sees the SIGTERM from . A multi-stage skeleton:
FROM node:22-alpine AS builder
WORKDIR /app
COPY package*.json ./
RUN npm ci
COPY . .
RUN npm run build
FROM node:22-alpine
WORKDIR /app
ENV NODE_ENV=production
COPY --from=builder /app/dist ./dist
COPY --from=builder /app/node_modules ./node_modules
USER node
EXPOSE 3000
CMD ["node", "dist/server.js"]The Dockerfile generator produces this shape for Node, Python, Go and others.
Gotchas
- means your user is not in the group. , then log out and in. If the socket is missing altogether, the daemon is not running: see Cannot connect to the Docker daemon.
- A container lives as long as its main process. exits immediately because with no terminal has nothing to do. Give it a real service, or for a shell.
- waits ten seconds and then kills. Apps that ignore SIGTERM (usually because the Dockerfile used the shell form of ) always take the full ten seconds and lose in-flight work.
- does not update running containers. Pull, then and again (or , which does this for you).
- deletes volumes of stopped containers, including databases. Leave off unless you mean it.
- refuses while any container, even a stopped one, references the image. finds them.
- Bind mount paths on must be absolute. only works in compose files; on the command line use .
- Anything beyond one or two containers belongs in a . The docker compose commands sheet covers the CLI and the file format.