Skip to content

Running Containers

Measured on Docker Desktop 4.81.0 / Engine 29.6.1 (macOS, linux/arm64), 2026-09-30.

An image is a blueprint. A container is a live, running instance of that blueprint — an isolated process with its own filesystem view, network, and process space, all sharing the host kernel.

You can run many containers from the same image, stop and restart them, inspect their logs, and remove them when you are done. Understanding this lifecycle is the foundation of working with Docker day to day.

The engine reports one of seven states in docker inspect --format '{{.State.Status}}' (the older four-state summary of “created, running, stopped, removed” leaves out the ones you will meet while debugging):

StateWhat it meansHow you get there (proven)
createdThe container exists but its process has never been started.docker create, Status=created
runningThe main process is executing.docker start / docker run
pausedProcesses are frozen with the cgroup freezer; memory stays allocated.docker pause → Status=paused Running=true Paused=true, ps shows Up … (Paused)
restartingA restart policy is between attempts after an exit.--restart always on a command that exits 1 → Status=restarting ExitCode=1, ps shows Restarting (1)
exitedThe main process ended (or docker stop). The container, its writable layer, logs and exit code still exist on disk.docker stop → Status=exited ExitCode=137 for a sleep that ignored SIGTERM
removingdocker rm is in progress. Very short-lived.Listed by the docker container ls status filter
deadA “defunct” container: removal only partly succeeded because something kept a resource busy. It cannot be restarted, only removed (per the docs). Rare — we could not produce one on demand.Same docs table

After docker rm completes there is no state at all: it deletes the container and its writable layer, and the container stops appearing anywhere.

flowchart LR
  created["created"] -->|docker start| running["running"]
  running -->|docker pause| paused["paused"]
  paused -->|docker unpause| running
  running -->|process exits or docker stop| exited["exited"]
  exited -->|docker start| running
  running -->|crash with a restart policy| restarting["restarting"]
  restarting --> running
  exited -->|docker rm| removed["gone (removed)"]
  created -->|docker rm| removed
Container states and the commands that move between them

The real docker inspect lines for the first four:

created Status=created Running=false Paused=false Restarting=false ExitCode=0
running Status=running Running=true Paused=false Restarting=false ExitCode=0
paused Status=paused Running=true Paused=true Restarting=false ExitCode=0
exited Status=exited Running=false Paused=false Restarting=false ExitCode=137
restarting Status=restarting Running=true Paused=false Restarting=true ExitCode=1

Note Running=true while paused or restarting: filter on .State.Status, not .State.Running, when you need the exact state.

docker run → created + running
docker stop → exited
docker start → running again (same container, same writable layer)
docker rm → removed (gone)
LessonTopic
Lifecycledocker run, docker ps, docker stop/start/restart, docker rm, --rm, exit codes
Exec & Logsdocker exec -it, docker logs, docker top, attaching, log rotation
Ports & EnvPublishing ports -p, environment variables -e / --env-file, naming --name
Restart & InspectRestart policies, docker inspect, docker stats, resource limits

The commands you will use most in this module:

scripts/quick-demo.sh
#!/bin/sh
# Pull and run nginx in the background
docker run -d --name demo nginx:1.31-alpine
# List running containers
docker ps
# Stop it
docker stop demo
# Remove it
docker rm demo
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
c0d6336221c2 nginx:1.31-alpine "/docker-entrypoint.…" 3 seconds ago Up 2 seconds 80/tcp demo

80/tcp with no arrow means the image declares port 80 (EXPOSE) but nothing is published to the host.

# Pull and run nginx detached
docker run -d --name demo nginx:1.31-alpine
# Confirm it is running
docker ps
# Stop the container
docker stop demo
# Remove it
docker rm demo
# Confirm it is gone
docker ps -a

An AI-written health probe for a deploy script:

🐛 Spot the bug

#!/bin/sh
# AI: "fail the deploy if the web container is not running"
if [ -z "$(docker ps -q --filter name=web)" ]; then
echo "web is down" >&2
exit 1
fi
echo "web is up"
Show the answer

--filter name= is a substring/regex match on the container name, not an equality test. If the real web container is gone but a container named webhook (or web-old) is running, the probe passes. Reproduced with names shortened from docker-b1-web / docker-b1-webhook (only the second container existed):

$ docker ps -q --filter name=web | wc -l
1
$ docker ps --filter name=web --format '{{.Names}}'
webhook
$ docker ps -q --filter 'name=^web$' | wc -l
0
$ docker inspect -f '{{.State.Running}}' web
error: no such object: web

Anchor the pattern, or better, ask about the exact container and its state:

scripts/check-web.sh
#!/bin/sh
set -eu
state=$(docker inspect -f '{{.State.Status}}' web 2>/dev/null || echo missing)
if [ "$state" != "running" ]; then
echo "web is $state" >&2
exit 1
fi
echo "web is up"

docker inspect on a missing container exits non-zero with no such object, which the || echo missing turns into a state instead of an accidental pass.

A container is a row in the engine’s database plus a process (when running) plus a writable layer on disk. docker stop only ends the process; the row and the layer stay until docker rm. Most confusion in this module — “where did my container go?”, “why is the disk full?”, “why does my name conflict?” — is forgetting that the row outlives the process.

ChoiceBenefitCost
Keep exited containersExit code, logs and writable layer stay inspectableThey accumulate disk and hold their names
--rmSelf-cleaning one-shot containersNothing left to inspect after a crash
docker pauseFreeze without losing memory state or PIDMemory stays allocated; network peers see a stalled service
  • “A stopped container is deleted.” It is exited and still listed by docker ps -a, with its writable layer.
  • “Running=true means the process is doing work.” A paused container also reports Running=true; check .State.Status.
  • “docker ps shows every container.” Only running ones (and paused/restarting). Add -a for the rest.
  • “docker ps --filter name=x finds container x.” It finds every container whose name contains or matches x.
Which state does a container enter immediately after 'docker stop'?
What is the difference between an image and a container?
After 'docker stop', can you start the container again?
After docker pause web, what do docker inspect and docker ps report?
A probe uses docker ps -q --filter name=web and passes although the web container was deleted. Why?