Want to host your own Docker Private Registry securely on Linux? In this step-by-step tutorial, you’ll learn how to deploy a *secure, self-hosted Docker Registry* using **Nginx reverse proxy, SSL encryption (SANs), and basic authentication**.
🔐 Perfect for DevOps engineers, developers, or anyone working with *CI/CD pipelines* and **container security**.
⏱️ *Timestamps:*
00:00 - Introduction
00:26 - Why You Need a Private Docker Registry
01:07 - Prerequisites
02:01 - Step 1: Generate SSL Certificate with SANs
04:39 - Step 2: Docker Compose Setup for Registry + Nginx
06:18 - Step 3: Configure Nginx Reverse Proxy with SSL
07:49 - Step 4: Add Basic Auth with htpasswd
09:13 - Step 5: Trust Self-Signed Cert on Docker Client
10:55 - Step 6: Push & Pull Docker Images Securely
13:23 - Troubleshooting Tips
📁 *Create SSL Certificates (with SANs):*
mkdir -p ~/private-registry/certs && cd ~/private-registry/certs
📄 `openssl.cnf` (update domain as needed):
[req]
distinguished_name = req_distinguished_name
req_extensions = v3_req
prompt = no
[req_distinguished_name]
C = US
ST = New York
L = New York
O = LinuxTechi
OU = IT Department
CN = registry.linuxtechi.org
[v3_req]
keyUsage = nonRepudiation, digitalSignature, keyEncipherment
extendedKeyUsage = serverAuth
subjectAltName = @alt_names
[alt_names]
DNS.1 = registry.linuxtechi.org
🔑 *Generate Key and Certificate:*
openssl genrsa -out registry.linuxtechi.org.key 2048
openssl req -new -key registry.linuxtechi.org.key -out registry.linuxtechi.org.csr -config openssl.cnf
openssl x509 -req -days 365 -in registry.linuxtechi.org.csr -signkey registry.linuxtechi.org.key -out registry.linuxtechi.org.crt -extensions v3_req -extfile openssl.cnf
📁 *Create Docker Compose Directory:*
mkdir -p ~/private-registry/nginx/conf.d
cd ~/private-registry
📝 *docker-compose.yml*
services:
registry:
image: registry:latest
ports:
"5000:5000"
environment:
REGISTRY_AUTH: htpasswd
REGISTRY_AUTH_HTPASSWD_REALM: Registry
REGISTRY_AUTH_HTPASSWD_PATH: /auth/registry.password
REGISTRY_STORAGE_FILESYSTEM_ROOTDIRECTORY: /registry-data
volumes:
./auth:/auth
./registry-data:/registry-data
restart: always
nginx:
image: nginx:latest
ports:
"80:80"
"443:443"
volumes:
./nginx/conf.d:/etc/nginx/conf.d
./certs:/etc/nginx/ssl
depends_on:
registry
restart: always
📝 *Nginx Reverse Proxy Config:*
vi ~/private-registry/nginx/conf.d/default.conf
server {
listen 80;
server_name registry.linuxtechi.org;
return 301 https://$host$request_uri;
}
server {
listen 443 ssl;
server_name registry.linuxtechi.org;
ssl_certificate /etc/nginx/ssl/registry.linuxtechi.org.crt;
ssl_certificate_key /etc/nginx/ssl/registry.linuxtechi.org.key;
ssl_protocols TLSv1.2 TLSv1.3;
ssl_ciphers 'EECDH+AESGCM:EDH+AESGCM:AES256+EECDH:AES256+EDH';
client_max_body_size 0;
chunked_transfer_encoding on;
location / {
proxy_pass http://registry:5000;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_read_timeout 900;
proxy_set_header Authorization $http_authorization;
proxy_pass_request_headers on;
proxy_buffering off;
}
}
🚀 *Start the Services:*
cd ~/private-registry
docker compose up -d
🔐 *Create Auth with `htpasswd`:*
sudo apt install apache2-utils -y
sudo htpasswd -Bc ~/private-registry/auth/registry.password devops
🔒 *Trust Certificate on Client Machine:*
sudo mkdir -p /etc/docker/certs.d/registry.linuxtechi.org:443
sudo cp registry.linuxtechi.org.crt /etc/docker/certs.d/registry.linuxtechi.org:443/ca.crt
sudo systemctl daemon-reload
sudo systemctl restart docker
📦 *Login and Push Image:*
docker login registry.linuxtechi.org:443
docker tag hello-world registry.linuxtechi.org:443/devops/my-app:latest
docker push registry.linuxtechi.org:443/devops/my-app:latest
🔄 *Test Pull:*
docker rmi registry.linuxtechi.org:443/devops/my-app:latest
docker pull registry.linuxtechi.org:443/devops/my-app:latest
🧰 *Common Issues & Fixes:*
✅ Certificate Error? - Check SANs in cert and Docker trust path.
✅ Login Failed? - Double-check `htpasswd` file + restart Docker.
✅ Nginx Error? - Validate paths in `default.conf` and view logs:
docker logs nginx_container_id
sudo tail -f /var/log/nginx/error.log
📌 *Subscribe for more DevOps tutorials* like this.
👍 Like & 💬 Comment if this helped you.
🔔 Don't forget to turn on the bell icon for updates!
#Docker #PrivateRegistry #DevOps #LinuxTechi #SelfHosted #ContainerSecurity #Nginx #SSL #DockerCompose #LinuxTutorial