How it works
The explanation, with examples you can run.
Anatomy of an image name
ghcr.io/acme/payments:1.4.2└─ registry ─┘└ repository ┘└ tag ┘ node:22-alpine is short for docker.io/library/node:22-alpineWith no registry, Docker assumes Docker Hub; with no namespace on Hub, library/ (the official images); with no tag, latest.
Tags versus digests
Ask the registry what a tag currently points to:
docker buildx imagetools inspect alpine:3.22# Name: docker.io/library/alpine:3.22# MediaType: application/vnd.oci.image.index.v1+json# Digest: sha256:5291449c3df73caf6ed85e649dec1b9e818b39a5d8c871e97afc13e9cd5e8fa8# Manifests:# Name: docker.io/library/alpine:3.22@sha256:3e9b4b68...# Platform: linux/amd64# ...The top-level digest is the image index (one entry per platform); each entry below has its own manifest digest. Tomorrow alpine:3.22 may point to a rebuilt index with a different digest (a patched package, a new base). The digest above will always mean exactly these bytes.
Pin by digest where reproducibility matters, and keep the tag for humans:
FROM alpine:3.22@sha256:5291449c3df73caf6ed85e649dec1b9e818b39a5d8c871e97afc13e9cd5e8fa8# Kubernetes: what runs is exactly what you testedimage: ghcr.io/acme/payments:1.4.2@sha256:<digest printed by your CI push>When both are present, the digest wins and the tag is ignored for resolution. Pin the index digest, not a single platform's manifest, or you lose the other architectures.
Living with pinned digests
Pinning only helps if the pins are updated: a base pinned for a year collects a year of vulnerabilities. Tools such as Renovate and Dependabot recognise tag@sha256: pins and open pull requests when the tag moves, so updates are deliberate, reviewed and revertible. For your own images, tag every build with something immutable by convention (the version or git SHA), never reuse a version tag, and have CI record the pushed digest for deployment.
Other things registries do
- Pull limits. Docker Hub limits anonymous and free pulls; CI that pulls a lot should authenticate or use a mirror or pull-through cache.
- Attestations and signatures. BuildKit can attach provenance and SBOM attestations to an image, and tools such as cosign sign a digest. Both refer to the digest, which is another reason to deploy by digest.
- Garbage. Untagged manifests are kept until the registry's retention or garbage collection removes them, so set lifecycle rules on private registries.
Check yourself
3 questions. Get them all right to finish this topic.
0 of 3 right so far. Get all three to finish this topic.