LearnAI ToolsCareerPractice BuildsPlayDevelopmentContact
Lesson 413 min read

Working with Images: pull, tags, layers and cleanup

Pull images from Docker Hub, understand tags, digests and layers, compare image sizes, tag your own copies and reclaim disk space.

On this page 12 sections

Introduction

Every container starts from an image, so choosing and managing images well matters: it affects how fast your containers download, how much disk they use and how secure they are. This lesson covers where images come from and how to work with them.

What You Will Learn
  • What Docker Hub and official images are.
  • How image names, tags and digests work.
  • Why the same software comes in images of very different sizes.
  • How images are built from layers, and how to tag, remove and clean up images.

Docker Hub and Official Images

Docker Hub (hub.docker.com) is the default registry: when you name an image without a registry, Docker looks there. Anyone can publish images to it, so prefer trusted sources:

KindExample nameWho publishes it
Docker Official Imagesnginx, python, postgres, alpineCurated and regularly updated in partnership with Docker
Verified publishersgrafana/grafana, bitnami/redisCompanies verified by Docker
Community imagespriya/quotes-apiAny user — check before trusting

The full name of an image is registry/namespace/repository:tag. Official images live in the library namespace, so nginx:alpine is short for docker.io/library/nginx:alpine — which is exactly what the pull output prints.

Pulling Images and Tags

docker run pulls images automatically, but docker pull downloads one without running it — useful to prepare a machine in advance:

docker pull nginx:alpine
Output

Click Run to see what this code prints.

A tag names a version or variant of an image. Popular images publish many tags — for example nginx:1.31, nginx:alpine or python:3.14-slim. If you leave the tag out, Docker uses latest, which simply means whatever the publisher last labelled that way — not necessarily the newest version, and it changes over time. Pulling again only downloads something if the tag now points to a different image:

docker pull nginx:alpine
Output

Click Run to see what this code prints.

The digest (sha256:...) identifies the exact image content and never changes. Tags can be moved to newer images; a digest cannot. When you need to be certain you are running exactly the same image, you can pull by digest: docker pull nginx@sha256:....

Listing Images

docker images
Output

Click Run to see what this code prints.

ColumnMeaning
IMAGEThe name and tag
IDThe start of the image’s unique ID (the same as its digest here)
DISK USAGESpace the image uses on your disk, unpacked
CONTENT SIZEThe compressed size — roughly how much is downloaded
EXTRAFlags such as U when a container is using the image

(The first line is a small legend that Docker 29 prints above the table when you use a terminal. docker image ls is the same command.)

Image Variants and Size

Most official images come in several variants. Priya compares two Python 3.14 images — slim (based on a trimmed-down Debian) and alpine (based on the tiny Alpine Linux). -q makes pull print only the image name:

docker pull -q python:3.14-slim
docker pull -q python:3.14-alpine
docker images python
Output

Click Run to see what this code prints.

VariantBased onGood for
python:3.14 (no suffix)Full Debian with many build toolsWhen you need to compile packages and do not care about size
python:3.14-slimMinimal DebianA safe default for most apps: small, and compatible with almost all packages
python:3.14-alpineAlpine Linux (musl instead of glibc)The smallest images, but some packages need extra work to install
Smaller Is Better

Smaller images download and start faster, cost less to store, and contain fewer programs that could have security vulnerabilities. This course uses slim images for Python apps and alpine images for tools such as Nginx, Redis and PostgreSQL.

Layers: docker history

An image is a stack of read-only layers. Each instruction in its Dockerfile adds a layer, and layers are shared: two images based on the same Alpine version store that base layer only once. That is why, in lesson 3, pulling nginx:alpine after alpine reported one layer as “Already exists” — the Alpine base layer was already on disk. docker history lists an image’s layers, newest first:

docker history nginx:alpine
Output

Click Run to see what this code prints.

Read from the bottom up: Alpine’s root filesystem (ADD alpine-minirootfs…), then Nginx being installed, configuration scripts copied in, the port it uses (EXPOSE) and the command it runs (CMD). Lines with size 0B only change settings. docker image inspect shows those settings directly:

docker image inspect nginx:alpine --format "Cmd: {{.Config.Cmd}} Ports: {{.Config.ExposedPorts}}"
Output

Click Run to see what this code prints.

Tagging and Removing Images

docker tag gives an image an extra name. It does not copy anything — both names point to the same image ID:

docker tag nginx:alpine my-nginx:1.0
docker images
Output

Click Run to see what this code prints.

docker rmi removes a name. Because nginx:alpine still points to the same image, only the tag is removed:

docker rmi my-nginx:1.0
Output

Click Run to see what this code prints.

Docker will not remove an image that a container is using, even a stopped one. Here Priya starts a container from python:3.14-alpine, then tries to remove the image:

docker run -d --name py python:3.14-alpine sleep 600
docker rmi python:3.14-alpine
Output

Click Run to see what this code prints.

Mini Challenge · Predict the Output

Priya runs docker tag nginx:alpine my-nginx:1.0. How much extra disk space does this use?

Choose one answer

Cleaning Up

Images take up a lot of space over time. After removing the container that was using it, Priya cleans up. docker image prune removes unused “dangling” images (left behind by rebuilds); with -a it removes every image not used by any container:

docker rm -f py
docker image prune -a -f
Output

Click Run to see what this code prints.

Over 300 MB reclaimed. Nothing is lost permanently — any image can be pulled again when it is needed. For a full clean-up of stopped containers, unused networks, unused images and the build cache, there is docker system prune (add -a for all unused images); docker system df shows how much space each kind of object uses.

Common Mistakes

Avoid These Mistakes
  • Relying on latest in production — it can change underneath you. Use a specific version tag.
  • Running images from unknown publishers without checking them.
  • Using full, non-slim base images by default and ending up with gigabyte-sized images.
  • Never cleaning up, then running out of disk space — check docker system df occasionally.

Frequently Asked Questions

Yes. Docker Hub limits how many images can be pulled per hour, with higher limits for users who are logged in (docker login) and for paid plans. Normal learning use stays well within the limits.

They are managed by the Docker daemon — on Linux under /var/lib/docker, and on Windows and macOS inside Docker Desktop’s virtual machine. Always manage them with docker commands rather than touching those files.

Those layers were built on another machine (the publisher’s), so their intermediate IDs are not available locally. It is normal for any pulled image.

Key Takeaways

  • Images are named registry/namespace/repository:tag; Docker Hub is the default registry.
  • Prefer official images and specific version tags; latest is just a moving label.
  • Digests identify exact image content; tags can move.
  • slim and alpine variants are far smaller than full images.
  • Images are stacks of shared layers; docker tag adds names, rmi removes them, prune reclaims space.

Summary

You can now find, choose and manage images. In the next lesson you will build your own image for Priya’s Python API by writing a Dockerfile.

Next Lesson →

Writing a Dockerfile: Containerise a Python App