10 Docker Commands Every Homelab Admin Should Know

The Commands That Actually Matter

Docker has over 50 commands. You’ll use about 10 of them regularly. The rest are either for building images, managing swarm clusters, or edge cases you’ll look up once a year. This guide covers the 10 commands I run most frequently across six Docker hosts, with the flags I actually use rather than every flag in the man page.

From the homelab: I run Docker across my entire homelab — from a Proxmox cluster to Raspberry Pis. Every self-hosted service I operate runs in containers. Knowing these commands inside out saves hours of troubleshooting.

I’m going to skip the installation basics here. If you haven’t got Docker running yet, follow our guides for Ubuntu 24.04, Debian 12, or Raspberry Pi first, then come back.

Every example uses real homelab scenarios. No abstract “mycontainer” names. If you’re running a homelab with Docker, these are the situations you’ll actually encounter.

Terminal showing docker ps output with multiple homelab containers running

1. docker ps – What’s Running Right Now

This is the command you’ll run most often. It shows all currently running containers.

docker ps

Output shows container ID, image, command, created time, status, ports, and name. On a busy host, the default output wraps and becomes unreadable. Use --format to clean it up:

# Clean, readable output
docker ps --format "table {{.Names}}\t{{.Status}}\t{{.Ports}}"

# Include stopped containers
docker ps -a

# Only show container IDs (useful for scripting)
docker ps -q

When you’ll use this: Every time you SSH into a Docker host. It’s your first check. “Is everything running?” Before you do anything else, run docker ps and make sure nothing has fallen over.

If you find yourself running docker ps --format with the same format string repeatedly, add an alias to your ~/.bashrc: alias dps='docker ps --format "table {{.Names}}\t{{.Status}}\t{{.Ports}}"'. Saves a lot of typing over time.

2. docker logs – What Went Wrong (or Right)

When a container crashes, misbehaves, or you just want to see what it’s doing, docker logs shows you the container’s stdout and stderr output.

# Show all logs for a container
docker logs portainer

# Follow logs in real time (like tail -f)
docker logs -f uptime-kuma

# Show last 50 lines
docker logs --tail 50 nginx

# Show logs with timestamps
docker logs -t grafana

# Combine: last 100 lines, then follow with timestamps
docker logs --tail 100 -ft nextcloud

When you’ll use this: When a container won’t start, when a service returns errors, or when you need to verify something is working. I check logs immediately after any docker compose up -d to make sure services started cleanly.

For Compose-managed containers, you can also use docker compose logs -f servicename from the project directory, which is slightly more convenient.

If you haven’t configured log rotation in your daemon.json, container logs grow without limit. I once had a Nextcloud container generate 12 GB of log data in a week. Check log sizes with docker system df -v and configure rotation as described in our Docker installation guide.

3. docker exec – Get Inside a Running Container

Sometimes you need to poke around inside a container. Maybe you need to check a config file, run a database query, or debug a networking issue. docker exec lets you run commands inside a running container.

# Open an interactive shell
docker exec -it nextcloud bash

# If bash isn't available (alpine images), use sh
docker exec -it redis sh

# Run a single command without entering the shell
docker exec mariadb mysql -u root -p -e "SHOW DATABASES;"

# Check what user a container runs as
docker exec portainer id

# View a file inside a container
docker exec nginx cat /etc/nginx/nginx.conf

The -it flags are almost always used together: -i keeps stdin open (interactive) and -t allocates a terminal. Without them, you get a non-interactive session that’s hard to use.

When you’ll use this: Debugging. A container is running but behaving oddly, and you need to see what’s happening from inside. Or you need to run a database migration, clear a cache, or check if a config file was mounted correctly. This is your “get inside and look around” tool.

Don’t make changes inside containers unless they’re persisted through a volume. Any modification to the container’s filesystem (outside of mounted volumes) is lost when the container restarts. If you need to change a config file, edit it on the host and restart the container.

4. docker compose up / down – Deploy and Tear Down

If you’re managing services with Docker Compose (and you should be), these are the commands that start and stop everything.

# Start all services in the background
docker compose up -d

# Stop and remove containers (volumes are preserved)
docker compose down

# Stop, remove, AND delete volumes (destructive - deletes data)
docker compose down -v

# Rebuild and restart (after changing a Dockerfile)
docker compose up -d --build

# Start only one specific service
docker compose up -d grafana

When you’ll use this: Every time you deploy, update, reconfigure, or troubleshoot a Compose-managed service. The typical workflow for updating a service is: docker compose pull (get latest images), then docker compose down && docker compose up -d.

For a deeper dive into Compose files, see our Docker Compose beginner’s guide.

Be very careful with docker compose down -v. The -v flag deletes named volumes, which is where your databases, application state, and persistent data live. I’ve seen people run this thinking it just stops containers. It doesn’t. It destroys data. Always double-check before adding -v.

5. docker system prune – Reclaim Disk Space

Docker accumulates cruft. Stopped containers, unused networks, dangling images (layers from previous builds that are no longer referenced), and build cache all consume disk space silently.

# See what's using space
docker system df

# Detailed breakdown
docker system df -v

# Remove stopped containers, unused networks, dangling images, build cache
docker system prune -f

# Also remove ALL unused images (not just dangling)
docker system prune -a -f

When you’ll use this: When your Docker host starts running low on disk space, or as part of regular monthly maintenance. I run docker system df weekly on all hosts and prune when reclaimable space exceeds a few gigabytes.

The difference between prune and prune -a matters. Without -a, it only removes “dangling” images (layers with no tag). With -a, it removes every image not used by a running container. If you’ve pulled images you plan to use later but haven’t started yet, -a will delete them.

6. docker stats – Live Resource Monitoring

A real-time view of CPU, memory, network, and disk I/O for all running containers. Think of it as top but for containers.

# Live stats for all containers
docker stats

# Stats for specific containers
docker stats nextcloud mariadb redis

# One-time snapshot (doesn't stream)
docker stats --no-stream

# Formatted output
docker stats --format "table {{.Name}}\t{{.CPUPerc}}\t{{.MemUsage}}"

When you’ll use this: When the host feels sluggish and you want to know which container is eating resources. When you’re deciding whether to add more RAM to a VM. When you want to verify that a memory limit you set in Compose is actually being respected.

Run docker stats --no-stream --format "table {{.Name}}\t{{.MemUsage}}\t{{.MemPerc}}" to get a quick snapshot of memory usage across all containers. I run this before deploying a new service to check if there’s enough headroom. On a Pi with 4 GB RAM, this becomes essential planning information.

7. docker inspect – The Full Story

When you need detailed information about a container, image, network, or volume, docker inspect gives you everything in JSON format. It’s verbose, but it answers questions that no other command can.

# Full inspection (verbose JSON)
docker inspect nextcloud

# Get just the IP address
docker inspect -f '{{range.NetworkSettings.Networks}}{{.IPAddress}}{{end}}' nextcloud

# Get mounted volumes
docker inspect -f '{{json .Mounts}}' nextcloud | jq

# Get environment variables
docker inspect -f '{{json .Config.Env}}' nextcloud | jq

# Check restart policy
docker inspect -f '{{.HostConfig.RestartPolicy.Name}}' nextcloud

When you’ll use this: Debugging networking issues (what IP does this container have?), verifying volume mounts are correct, checking what environment variables a container received, or finding out why a container’s restart policy isn’t working as expected.

The -f flag uses Go template syntax, which is awkward at first but powerful for extracting specific fields. Pipe to jq for readable JSON output.

8. docker network ls – Understanding Container Networking

Shows all Docker networks on the host. Each Compose project creates its own network, and understanding this helps debug connectivity issues.

# List all networks
docker network ls

# Inspect a specific network (shows which containers are connected)
docker network inspect bridge

# See which containers are on a network
docker network inspect monitoring_default --format '{{range .Containers}}{{.Name}} {{end}}'

When you’ll use this: When containers can’t reach each other. When you’re setting up cross-project networking (containers from different Compose files that need to communicate). When you want to verify that a container is on the network you expect.

Each Compose project creates a network named projectdirectory_default. Containers within that project can reach each other by service name. Containers on different networks can’t talk to each other unless you explicitly connect them or use an external network.

9. docker volume ls – Where Your Data Lives

Lists all Docker-managed volumes. These are the named volumes defined in your Compose files (or created manually) that persist container data.

# List all volumes
docker volume ls

# See detailed info about a volume
docker volume inspect nextcloud_nc_data

# Find volumes that aren't used by any container
docker volume ls -f dangling=true

# Remove unused volumes (careful!)
docker volume prune -f

When you’ll use this: When you need to find where a container’s data is stored on disk. When you’re backing up persistent data. When you’re cleaning up after removing old services and want to reclaim the volume space.

Treat docker volume prune with the same caution as rm -rf. It deletes volumes not attached to any running container. If you’ve stopped a service temporarily and its volumes are “dangling,” prune will destroy your data. Always check what’s dangling with docker volume ls -f dangling=true before pruning.

10. docker pull – Get the Latest Images

Downloads the latest version of an image from the registry. This is how you update your containers to the newest release.

# Pull a specific image
docker pull portainer/portainer-ce:latest

# Pull all images defined in a Compose file
docker compose pull

# Pull a specific service from a Compose file
docker compose pull grafana

When you’ll use this: Before updating services. The update workflow is: docker compose pull to download new image versions, then docker compose down && docker compose up -d to replace the running containers with the updated images.

docker compose pull is the one you’ll use most often, as it pulls updated images for all services in your Compose file at once.

Not all image updates are safe. Pulling latest for an application is usually fine, but pulling latest for a database can jump major versions and break things. Pin database images to specific versions (e.g., mariadb:10.11, postgres:16) and upgrade those deliberately after reading the release notes.

Bonus: Quick Combinations

These aren’t individual commands but combinations I use frequently enough that they’re worth mentioning:

# Restart a single container
docker restart nextcloud

# Stop all running containers (emergency brake)
docker stop $(docker ps -q)

# Remove all stopped containers
docker container prune -f

# Watch container logs across an entire Compose project
docker compose logs -f --tail 20

# Check if a container can reach the internet
docker exec nextcloud ping -c 3 1.1.1.1

# Check DNS resolution inside a container
docker exec nextcloud nslookup google.com

# Copy a file from a container to the host
docker cp nextcloud:/var/www/html/config/config.php ./config-backup.php

# See the last time a container was restarted
docker inspect -f '{{.State.StartedAt}}' nextcloud

Printable Cheat Sheet

Here’s a condensed reference you can keep handy. Print it, bookmark it, or save it to your notes app.

Command Purpose Key Flags
docker ps List running containers -a (all), -q (IDs only), --format
docker logs NAME View container output -f (follow), --tail N, -t (timestamps)
docker exec -it NAME bash Shell into a container -it (interactive terminal)
docker compose up -d Start Compose services -d (detached), --build (rebuild)
docker compose down Stop Compose services -v (delete volumes too)
docker system prune -f Clean up unused resources -a (include unused images)
docker stats Live resource usage --no-stream (snapshot), --format
docker inspect NAME Detailed container/network info -f (format/filter)
docker network ls List Docker networks inspect NAME for details
docker volume ls List persistent volumes -f dangling=true (unused)
docker pull IMAGE Download/update an image docker compose pull for stacks

In interviews for infrastructure and DevOps roles, you’ll often be asked to troubleshoot a scenario involving Docker. Knowing docker logs, docker exec, docker inspect, and docker stats gives you a methodical troubleshooting approach: check the logs, get inside the container, inspect the configuration, monitor resources. That systematic approach matters more than memorising every flag. Interviewers want to see how you think through problems, not whether you’ve memorised the man pages.

Practitioner tip: If a container keeps restarting and you cannot read the logs because they scroll too fast, use docker logs --tail 50 container_name to grab the last 50 lines. Pair with --timestamps when you need to correlate events with other services.

Key Takeaways

  • docker ps is your first command on any Docker host. Make it a habit
  • docker logs -f is your primary debugging tool. Check logs after every deployment
  • docker exec -it gets you inside a container for hands-on debugging, but don’t make changes that aren’t persisted through volumes
  • docker compose up -d and docker compose down are your daily deployment commands. Never use down -v unless you want to delete data
  • docker system prune prevents disk space problems, but prune -a removes images you might want to keep
  • docker stats shows you which container is consuming resources in real time
  • docker inspect answers the detailed questions: IP address, mounts, environment variables, restart policy
  • Pin database images to specific versions. Use latest for applications, but update databases deliberately
  • Combine docker compose pull followed by down and up -d for routine service updates

Related Guides

If you found this useful, these guides continue the journey:

The RTM Essential Stack - Gear I Actually Use

Enjoyed this guide?

New articles on Linux, homelab, cloud, and automation every 2 days. No spam, unsubscribe anytime.

Scroll to Top