
Docker makes it easy to spin up services fast, but that convenience comes with a side effect: unused images, stopped containers, stale volumes, and orphaned networks pile up quietly and consume disk space. This guide covers every practical method to remove Docker images, remove Docker volumes, remove Docker containers, and clean up networks, whether you need a targeted one-liner or a full system wipe.
Quick Cleanup with docker system prune
Before targeting individual resources, it is worth knowing that Docker ships with a single command capable of reclaiming a significant amount of space in one shot: docker system prune. This is the fastest path to a clean environment when you are not concerned about being selective.
Default Prune vs Full Prune
Running docker system prune without any flags removes stopped containers, dangling images (images not tagged and not referenced by any container), unused networks, and the build cache. It does not touch volumes by default, and it does not remove images that are simply unused but still tagged.
docker system prune Docker will prompt for confirmation before proceeding. If you want to skip the prompt in automated scripts, add the -f or –force flag.
To perform a more thorough docker cleanup that removes all unused images, not just dangling ones, and also removes unused volumes, use the combined flags:
docker system prune -a --volumes This is the most complete single-command option available and covers nearly every category of unused Docker resource at once. Use it with care on shared hosts or production machines, since it removes every image not currently attached to a running container.
Using Filters with Prune Commands
Most prune commands accept a –filter flag that lets you scope the cleanup by label or creation time. This is documented in the official docker system prune documentation and applies across docker image prune, docker container prune, docker volume prune, and docker network prune as well.
For example, to remove only resources older than 24 hours:
docker system prune --filter "until=24h" You can also filter by label when your workflow assigns labels to images or containers:
docker system prune --filter "label=environment=staging" The same –filter syntax works with docker images –filter and docker ps –filter when you want to list or act on specific subsets before pruning. For instance, docker images –filter dangling=true lists only untagged images, and docker ps –filter status=exited lists only stopped containers.
Removing Docker Volumes
Volumes are intentionally excluded from most automatic cleanup commands because they store persistent data. Docker does not remove a volume when its associated container is deleted unless you explicitly tell it to. This means volumes can accumulate over time, especially in active development environments.
List and Inspect Volumes
Before removing anything, get a clear picture of what exists. The docker volume ls command lists all volumes on the host:
docker volume ls To understand what docker volumes are in more detail: volumes are directories managed by Docker, stored outside the container’s writable layer. They survive container restarts and removals, which is exactly what makes them useful for databases and persistent application state, but also what makes them easy to forget about.
To list only unused or docker dangling volumes, those not currently mounted by any container, use the filter flag:
docker volume ls -f dangling=true 
This gives you a focused list of candidates for cleanup without touching anything in active use.
Remove a Specific Volume
Once you have identified the volume you want to delete, the docker volume rm command removes it by name:
docker volume rm my_volume You can remove multiple volumes in a single call by providing additional names:
docker volume rm volumeone volumetwo volume_three To docker remove a volume by name, you need to know the exact name as it appears in the docker volume ls output. Anonymous volumes have auto-generated names; named volumes use whatever name was defined in the docker-compose.yml or passed at runtime.
Remove All Unused Volumes
To remove all volumes not currently in use by a container, docker volume prune is the right command:
docker volume prune This removes every volume not attached to at least one container, whether running or stopped. It will prompt for confirmation before proceeding. To prune volumes without a prompt, add the –force flag:
docker volume prune --force If you want to docker remove all volumes unconditionally, including those attached to stopped (but not removed) containers, you need to remove those containers first and then run docker volume prune. There is no native Docker command to force-delete every volume without first stopping and removing associated containers.
Remove a Volume That Is in Use
If you try to docker remove a volume that is in use by a running or stopped container, the command will fail with an error stating the volume is in use:
Error response from daemon: remove myvolume: volume is in use – [containerid]
To resolve a docker volume rm error where the volume is in use, you need to remove the container first:
docker rm container_id Then retry:
docker volume rm my_volume If the container is running, stop it first:
docker stop container_id docker rm container_id docker volume rm my_volume There is no –force option for docker volume rm that overrides the in-use check. The only path forward is removing the dependent container first.
Remove Containers and Associated Volumes Together
When you delete a container, Docker does not automatically remove its associated volume unless you pass the -v flag. This is the docker rm with volumes option:
docker rm -v container_name This removes the container and any anonymous volumes attached to it. Named volumes are not removed by this flag, even with -v, because named volumes are considered managed resources that may be intentionally shared across containers. If you want to also remove a named volume, you must specify it separately with docker volume rm.
This distinction matters: docker rm does remove volumes only for anonymous volumes. Named volumes persist until you explicitly remove them.
Removing Docker Images
Images are the largest contributors to Docker disk usage. Every docker pull, docker build, and docker-compose up can add layers to your local image store. Regular cleanup with docker rmi and docker image prune keeps this under control.
Remove a Specific Image
To docker remove an image by name or tag, use the docker image rm command or its shorthand docker rmi:
docker rmi ubuntu:22.04 You can also reference images by their image ID, which you can find by running docker images -a:
docker images -a docker rmi a1b2c3d4e5f6 If you want to delete multiple images at once, list their IDs or tags separated by spaces:
docker rmi imageone imagetwo image_three The docker rmi command and docker image rm are functionally identical. Either works for the docker delete image workflow.
Remove Dangling Images
Docker dangling images are image layers that have lost their association with a tagged image, typically because a new build replaced an older version and the old layers were left behind. They appear as <none>:<none> in the docker images output.
To list dangling images:
docker images -f dangling=true To remove dangling images in Docker, use docker image prune:
docker image prune This targets only the untagged, unreferenced layers and is safe to run regularly. It will ask for confirmation before deleting anything.
Remove All Unused Images
To go further and remove all images not referenced by at least one container (running or stopped), use docker image prune -a:
docker image prune -a This is considerably more aggressive than the default prune. It removes every image your system has pulled that is not currently in use, so any future docker run command referencing those images will require a fresh pull. Use this when reclaiming space on a build server or CI runner between jobs.
Force-Remove an Image in Use by a Stopped Container
If a docker remove image operation fails because the image is still referenced by a stopped container, you have two options.
The first is to remove the stopped container first, then remove the image:
docker rm container_id docker rmi image_name The second is to use the –force flag to docker force remove the image regardless of stopped container references:
docker rmi --force image_name Note that –force bypasses the reference check for stopped containers but will not forcibly remove an image that is actively in use by a running container. In that case, you must stop the container first.
Removing Docker Containers
Containers are the most frequently created and discarded Docker resource. Even short-lived containers, test runs, and failed builds leave entries that accumulate quickly in the docker ps -a output.
Remove a Specific Container
The docker rm command deletes a container by name or ID. Use docker ps -a to list all containers including stopped ones:
docker ps -a To remove a container by name:
docker rm my_container To docker remove a container by ID:
docker rm a1b2c3d4e5f6 The docker rm command only works on containers that are not currently running. Attempting to remove a running container returns an error.
Remove All Stopped Containers
To clean up every container that is not currently running, docker container prune is the most direct option:
docker container prune This removes all stopped and exited containers in one pass and prompts for confirmation. To skip the prompt:
docker container prune --force Alternatively, you can combine docker ps filters with docker rm to target specific states. To docker remove all exited containers:
docker rm $(docker ps -a -f status=exited -q) This approach also supports chaining multiple filters. To remove all stopped containers matching either exited status or a specific name pattern:
docker rm $(docker ps -a -f status=exited -f name=test -q) Force-Remove a Running Container
To force-remove a running container without stopping it first, pass the –force flag to docker rm:
docker rm --force container_name This sends a SIGKILL to the container process and removes it immediately. It is equivalent to running docker stop followed by docker rm, but in a single step. Use this when a container is unresponsive or when you need to docker stop and remove a container quickly in a script.
Auto-Remove Containers on Exit
If you know a container is ephemeral, for example a test runner or a one-off script, you can instruct Docker to automatically remove the container when it exits using the –rm flag at startup:
docker run --rm image_name The container will be removed immediately when the process inside it completes, whether it exits cleanly or with an error. This is the cleanest way to docker remove a container after stop without any manual cleanup step.
Stop and Remove All Containers
To stop and remove every container on the host, combine docker stop and docker rm with the full container list:
docker stop $(docker ps -a -q) docker rm $(docker ps -a -q) Run these two commands in sequence. The first stops all running containers, and the second removes all containers (now stopped). This is the docker remove all containers command pattern used most commonly in development environment resets.
Removing Docker Networks
Custom Docker networks persist after the containers using them are removed. Over time, networks from old projects and abandoned Compose stacks can accumulate and interfere with new deployments.
Remove Specific and Unused Networks
To list all networks on the host:
docker network ls In order to remove a specific network by name:
docker network rm my_network Last but not least, remove all networks not currently used by at least one container, use docker network prune:
docker network prune This covers the most common cleanup scenario and is safe to run alongside volume and image pruning. For a complete cleanup of all Docker resources in one pass that covers containers, images, volumes, and networks, the previously covered docker system prune -a –volumes command handles everything.
Docker Compose Cleanup
Projects managed with Docker Compose require a slightly different cleanup approach because Compose tracks relationships between services, volumes, and networks as a unit.
Docker Compose Down with Volumes and Images
The base command to stop and remove Compose-managed containers, networks, and the default network is:
docker compose down This does not remove volumes or images by default. To also remove volumes, add the -v flag:
docker compose down -v The docker compose down -v command removes both anonymous volumes and named volumes defined in the Compose file’s volumes section. This is one of the key differences from docker rm -v, which only handles anonymous volumes.
To also remove all images used by the services in the Compose file, add –rmi all:
docker compose down --rmi all Combining both flags gives you a full teardown:
docker compose down -v --rmi all This removes all containers, networks, named and anonymous volumes, and all associated images. It is the equivalent of a clean project reset.
Remove Orphaned Compose Resources
When you modify a docker-compose.yml file and remove a service, the containers for that service are not automatically cleaned up by subsequent docker compose down runs. They become orphaned resources.
To include orphaned containers in the cleanup:
docker compose down --remove-orphans This flag tells Compose to remove containers for services that are no longer defined in the current Compose file. You can combine it with -v to also clean up any volumes left behind by those removed services:
docker compose down -v --remove-orphans Clearing the Build Cache
The Docker build cache stores intermediate image layers from previous builds. On active development machines and CI systems, the cache can grow to several gigabytes quickly. Clearing it does not affect running containers or existing images, only the cached build layers.
Docker Builder Prune Options
To docker clear the cache, use docker builder prune:
docker builder prune This removes all dangling build cache entries (layers not referenced by any existing image). For a more thorough docker disk cleanup that removes the entire build cache, add the -a flag:
docker builder prune -a The -a flag removes all build cache, including cache that is still referenced. This forces the next build to start completely fresh, which takes longer but guarantees a clean state.
To filter by age, for example to remove only cache entries older than 48 hours, use:
docker builder prune --filter "until=48h" This is useful in CI environments where you want to preserve recent cache for faster builds while still reclaiming space from stale entries.
Frequently Asked Questions
No, not by default. Running docker system prune without any flags skips volumes entirely to avoid accidental data loss. To include volumes in the prune operation, you must explicitly pass the –volumes flag: docker system prune –volumes. For a complete cleanup, use docker system prune -a –volumes, which removes all unused images, stopped containers, unused networks, the build cache, and unused volumes in a single pass.
The docker rm command removes containers, while the docker rmi command removes images. You cannot use docker rm on an image or docker rmi on a container. The docker rm command accepts container names or IDs, and the docker rmi command accepts image names, tags, or image IDs. If you are unsure which to use, check first: docker ps -a lists containers and docker images -a lists images.
You cannot remove a volume that is currently mounted by a container, whether that container is running or stopped. Docker will return an error indicating the volume is in use. The solution is to first remove the container using that volume with docker rm containerid, and then remove the volume with docker volume rm volumename. If the container is running, stop it first with docker stop container_id before removing it.
Yes. Unlike docker rm -v, which only removes anonymous volumes, docker compose down -v removes both anonymous and named volumes that are declared in the volumes section of the docker-compose.yml file. If a named volume is shared between multiple Compose projects and is still in use by another project, it will not be removed. Volumes defined externally using external: true in the Compose file are also excluded from removal.
The fastest way to docker clean all resources, including images, containers, volumes, and networks, is:
docker system prune -a –volumes –force
The -a flag extends the cleanup to all unused images (not just dangling ones), –volumes adds unused volumes to the scope, and –force skips the confirmation prompt. This is the most complete single-command option for clearing a Docker environment. Be aware that this will not remove volumes or images that are currently in use by running containers, so any actively running services are left untouched.