Let's assume that the FQDN name of the server will be registry.localdomain, and the service will be exposed as https://registry.localdomain:8443/.
Create an environment file .env for the docker-compose project. An example content:
COMPOSE_PROJECT_NAME=registry_localdomain
Create the docker volume for the registrt data (images etc); e.g.:
docker volume create registry-1-data
Create a folder certs containing the key (server.key) and the certificate (server.crt) to use for the HTTPS service.
If the certificate is an intermediate certificate (i.e is not directly signed by the CA), then server.crt must contain all intermediate certificates starting from the bottom level (i.e. the one for registry.localdomain).
Create the docker network (must be named as <project_name>_default); e.g.:
docker network create --attachable registry_localdomain_default
Prepare a password file in the htpasswd format. It will store the credentials for basic HTTP authentication to the registry.
Copy the output line from htpasswd command (e.g for a user named admin):
docker run -it --entrypoint htpasswd registry:2 -Bn admin
Append the output line to a file named htpasswd (in the project directory).
Prepare the compose file:
version: '3.7'
services:
registry:
image: registry:2
environment:
REGISTRY_HTTP_ADDR: '0.0.0.0:443'
REGISTRY_HTTP_TLS_CERTIFICATE: "/certs/server.crt"
REGISTRY_HTTP_TLS_KEY: "/certs/server.key"
REGISTRY_STORAGE_DELETE_ENABLED: 'true'
REGISTRY_AUTH: 'htpasswd'
REGISTRY_AUTH_HTPASSWD_REALM: 'Registry Realm'
REGISTRY_AUTH_HTPASSWD_PATH: /htpasswd
hostname: registry-1
restart: always
volumes:
- type: bind
source: "$PWD/certs"
target: "/certs"
read_only: true
- type: bind
source: "$PWD/htpasswd"
target: "/htpasswd"
read_only: true
- type: volume
source: 'registry-1-data'
target: '/var/lib/registry'
ports:
- '8443:443'
volumes:
'registry-1-data':
external: trueCreate the containers:
docker-compose up --no-start
Start:
docker-compose start
To use the registry as a client (pull/push images), we must first trust the authority (CA) that signed the service's certificate.
Let localdomain.crt be the root certificate that signed the certificate for registry.localdomain.
Copy localdomain.crt under /usr/local/share/ca-certificates/.
Update system's bundle of trusted certificates:
update-ca-certificates
Restart docker so that it reads the updated certificate bundle.
Tag an image:
docker tag tomcat:8.5 registry.localdomain:8443/tomcat:8.5
Login to the registry:
docker login -u admin registry.localdomain:8443
Push and pull images. For example:
docker push registry.localdomain:8443/tomcat:8.5
docker pull registry.localdomain:8443/tomcat:8.5
To interact with the service in any other way (except from pushing images) you need the REST API. See https://docs.docker.com/registry/spec/api/#detail
In order to delete an image, first you must find the reference as a digest. For example for tomcat:8.5 image:
curl -v -H 'Accept: application/vnd.docker.distribution.manifest.v2+json' \
https://registry.localdomain:8443/v2/tomcat/manifests/8.5
The reference is the value of the Docker-Content-Digest response header.
Delete the image:
curl XDELETE -v \
https://registry.localdomain:8443/v2/tomcat/manifests/sha256:c3055399ebfef5d782c50fd5ca98455ebe9f7e4400f1371a54869393e5912bb9
The above will unlink the referenced image, but the underlying blobs will be still present in the filesystem. To delete them you must run the garbage collector (see https://docs.docker.com/registry/garbage-collection/). For example run inside the container (/etc/docker/registry/config.yml is where registry reads its configuration):
docker-compose exec registry bin/registry garbage-collect /etc/docker/registry/config.yml