├── Dockerfile ├── LICENSE ├── README.md ├── nginx ├── ca.pem ├── docker-registry.default ├── docker-registry.htpasswd ├── nginx.conf ├── server.crt └── server.key └── start.sh /Dockerfile: -------------------------------------------------------------------------------- 1 | FROM ubuntu:trusty 2 | ENV DEBIAN_FRONTEND noninteractive 3 | 4 | MAINTAINER Larry Cai 5 | 6 | ENV REFREST_AT 20150115 7 | 8 | # nginx 9 | RUN apt-get update -q \ 10 | && apt-get install -yf build-essential python-software-properties software-properties-common \ 11 | && add-apt-repository ppa:nginx/stable \ 12 | && apt-get update -q \ 13 | && apt-get -y install -y curl 14 | 15 | ENV NGINX_VERSION 1.7.9 16 | # build nginx from source with http auth module enabled 17 | RUN apt-get -y install libpcre3-dev zlib1g-dev libssl-dev bsdtar libldap2-dev 18 | 19 | # use bsdtar for zip file 20 | RUN curl -Ls https://github.com/kvspb/nginx-auth-ldap/archive/master.zip | bsdtar -xf- -C /tmp \ 21 | && curl -s http://nginx.org/download/nginx-${NGINX_VERSION}.tar.gz | tar -xz -C /tmp \ 22 | && cd /tmp/nginx-${NGINX_VERSION} \ 23 | && ./configure --add-module=../nginx-auth-ldap-master --with-http_ssl_module --with-http_auth_request_module && make && make install 24 | 25 | # put self signed ssl key (generated by htpasswd 26 | RUN apt-get -y install apache2-utils 27 | 28 | ADD . /app 29 | RUN chmod +x /app/start.sh && mkdir /data 30 | 31 | VOLUME ["/data"] 32 | 33 | EXPOSE 80 443 3443 34 | CMD /app/start.sh 35 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | Copyright (c) 2014, OpenDNS, Inc. 2 | All rights reserved. 3 | 4 | Redistribution and use in source and binary forms, with or without 5 | modification, are permitted provided that the following conditions are met: 6 | 7 | * Redistributions of source code must retain the above copyright notice, this 8 | list of conditions and the following disclaimer. 9 | 10 | * Redistributions in binary form must reproduce the above copyright notice, 11 | this list of conditions and the following disclaimer in the documentation 12 | and/or other materials provided with the distribution. 13 | 14 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 15 | AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 16 | IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 17 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE 18 | FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 19 | DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR 20 | SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER 21 | CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, 22 | OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 23 | OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 24 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Nginx authentication proxy, works with private docker registry # 2 | 3 | * HTTP Basic Auth 4 | * LDAP Authentication 5 | 6 | Below links are referred: 7 | 8 | * Dockerfile is based on https://github.com/opendns/nginx-auth-proxy for nginx env, but totally changed for this 9 | * nginx config is referred https://github.com/docker/docker-registry/issues/747#issuecomment-64952999 10 | * https://github.com/docker/docker-registry/tree/master/contrib/nginx 11 | * https://calvin.me/nginx-ldap-http-authentication/ 12 | * http://www.allgoodbits.org/articles/view/29 13 | 14 | Try to run nginx docker container in front of registry container 15 | 16 | ## HTTP Basic Authentication 17 | 18 | Mostly it follows the blog [Building private Docker registry with basic authentication]( 19 | https://medium.com/@deeeet/building-private-docker-registry-with-basic-authentication-with-self-signed-certificate-using-it-e6329085e612) 20 | 21 | """ All the certifications inside are generated for demo purpose inside. """ 22 | 23 | It works successfully under boot2docker windows environment. 24 | 25 | You need to append `dokk.co` (testing domain name) in `/etc/hosts`'s `localhost` 26 | 27 | 127.0.0.1 boot2docker localhost localhost.local dokk.co 28 | 29 | Download and add [ca.pem](https://github.com/larrycai/nginx-auth-proxy/blob/master/) into your ca trust list. 30 | 31 | $ cat ca.pem | sudo tee -a /etc/ssl/certs/ca-certificates.crt 32 | $ sudo /etc/init.d/docker restart 33 | 34 | Then you can start two docker containers to try 35 | 36 | $ docker run -d --name registry -p 5000:5000 registry 37 | $ docker run -d --name nginx --link registry:registry -p 443:443 larrycai/nginx-registry 38 | 39 | It recommend to put `docker-registry.htpasswd`,`server.crt`,`server.key` put local directory like `/registry-key` and passed via tag `volume` 40 | 41 | $ docker run -d --name registry -p 5000:5000 registry 42 | $ docker run -d --name nginx -v /registry-key:/data --link registry:registry -p 443:443 larrycai/nginx-registry 43 | 44 | ### Verify ### 45 | 46 | open browser to access https://192.168.59.103 , it shall show the nginx https works fine. 47 | 48 | Now verify the https basic auth is ok 49 | 50 | $ curl -i -k https://larrycai:passwd@dokk.co 51 | 52 | Then we see `docker push` is ok 53 | 54 | $ docker login -u larrycai -p passwd -e "test@gmail.com" dokk.co 55 | $ docker pull hello-world 56 | $ docker tag hello-world dokk.co/hello-world 57 | $ docker push dokk.co/hello-world 58 | $ docker pull dokk.co/hello-world 59 | 60 | ## LDAP Authentication 61 | 62 | With the help of 3rd nginx module [nginx_auth_ldap](https://github.com/kvspb/nginx-auth-ldap), it can be configured to have LDAP authentication. 63 | 64 | Below is the sample how it works with simple LDAP server, surely you need to adjust the configuration for your own solution. 65 | 66 | ### Verify ### 67 | 68 | It use another docker image [larrycai/openldap](https://registry.hub.docker.com/u/larrycai/openldap/) as sample 69 | 70 | $ docker run -d --name registry -p 5000:5000 registry 71 | $ docker run -d -p 389:389 --name ldap -t larrycai/openldap 72 | $ docker run -d --name nginx --link ldap:ldap --link registry:registry -p 443:443 -p 3443:3443 larrycai/nginx-registry 73 | 74 | Then you can repeat the verification like basic authentication. (don't forget to change `dock.co` to `dock.co:3443`) 75 | 76 | 77 | -------------------------------------------------------------------------------- /nginx/ca.pem: -------------------------------------------------------------------------------- 1 | -----BEGIN CERTIFICATE----- 2 | MIIDmTCCAoGgAwIBAgIJAKBk32pxWW61MA0GCSqGSIb3DQEBCwUAMGMxCzAJBgNV 3 | BAYTAkNOMQswCQYDVQQIDAJTSDELMAkGA1UEBwwCU0gxITAfBgNVBAoMGEludGVy 4 | bmV0IFdpZGdpdHMgUHR5IEx0ZDEXMBUGA1UEAwwObGFycnljYWl5dS5jb20wHhcN 5 | MTQxMTI5MDY0MDExWhcNMTUxMTI5MDY0MDExWjBjMQswCQYDVQQGEwJDTjELMAkG 6 | A1UECAwCU0gxCzAJBgNVBAcMAlNIMSEwHwYDVQQKDBhJbnRlcm5ldCBXaWRnaXRz 7 | IFB0eSBMdGQxFzAVBgNVBAMMDmxhcnJ5Y2FpeXUuY29tMIIBIjANBgkqhkiG9w0B 8 | AQEFAAOCAQ8AMIIBCgKCAQEAybzvJc6Ii+Q78ufG+ak1e7CGylkfcvE0o6Zp2lBv 9 | /pie5nJJPkdoh2ClvMPlzAVY8C+7PMkxUhdIoPZSyF8RvpLqS9vGy/YkdAxg31db 10 | bSzXQYAPtIrLevL8r695D+80JOSLCr6UZVVyKMVL3rms6WcAqAsm92gzqnHT1+0H 11 | e6MjssuiP2LspqcTI8G4LcHrQs2u2SHWm/E4pTzuvxK3c6VGzZkQfaoLZSmkpWCn 12 | AAtDpJSKzlOT23OFIW4WYbSemOeVHwPp/GSAosY8cljpPnyV5HV/ioSSuFzNRjzU 13 | ifJJIULkZlON1p0fj4PcXojQHl3oBCArRtjfgdoIhjQhIQIDAQABo1AwTjAdBgNV 14 | HQ4EFgQURsRMgH8M4qOnq/KAeXjKWtR6llowHwYDVR0jBBgwFoAURsRMgH8M4qOn 15 | q/KAeXjKWtR6llowDAYDVR0TBAUwAwEB/zANBgkqhkiG9w0BAQsFAAOCAQEAc7VX 16 | 8iebzPig5tQ1PVa83Q0xkbsub58moxxc27S54jKWwBQeB6bR58VluUKXh9PfjrOU 17 | tSrvgsvQ4TqLZ9T6Yt/4jzn46ILbPjFAw3Te0UH0XwmJbk/FZzDj4xP0S6UHk2hU 18 | f1MjiJEQq9LlOFKCKUMkF1MRPh+Nn3WlZjBPvmNXx6B5hW5ssHmcVn0UbohdaVYt 19 | 6vAc2g19X27b9DGJOUuSfhMnGPzJnh0PGoHanEgBKjiKMhK9czCz/MKkOgrHXtYQ 20 | p/TxMpe7i+e8UIdMDJtrP0OBNlu4NWPoXL5yoPaZrX+FAwjojFIbvCXI2mVjUJg1 21 | h9Q8jlD3G03BYT+tXQ== 22 | -----END CERTIFICATE----- 23 | -------------------------------------------------------------------------------- /nginx/docker-registry.default: -------------------------------------------------------------------------------- 1 | upstream docker-registry { 2 | server registry:5000; 3 | } 4 | server { 5 | listen 80; 6 | location / { 7 | rewrite ^(.*)$ https://$host$1 last; 8 | } 9 | } 10 | 11 | 12 | server { 13 | # https://github.com/docker/docker-/issues/747#issuecomment-64957116 14 | listen 443; 15 | 16 | ssl on; 17 | ssl_certificate /data/server.crt; 18 | ssl_certificate_key /data/server.key; 19 | 20 | location / { 21 | limit_except GET HEAD OPTIONS { 22 | auth_basic "Restricted"; 23 | auth_basic_user_file /data/docker-registry.htpasswd; # testuser:testpasswd & larrycai:passwd 24 | } 25 | proxy_set_header X-Forwarded-Proto $scheme; 26 | proxy_set_header Host $http_host; 27 | proxy_set_header X-Real-IP $remote_addr; 28 | client_max_body_size 800M; # avoid HTTP 413 for large image uploads 29 | chunked_transfer_encoding on; # required to avoid HTTP 411: see Issue #1486 (https://github.com/dotcloud/docker/issues/1486) 30 | proxy_pass http://docker-registry; 31 | } 32 | } 33 | 34 | # LDAP http://www.allgoodbits.org/articles/view/29 35 | 36 | ldap_server ldap1 { 37 | url ldap://ldap:389/ou=Users,dc=openstack,dc=org?uid?sub?(objectClass=inetOrgPerson); 38 | #binddn "TEST\\LDAPUSER"; 39 | #binddn_passwd LDAPPASSWORD; 40 | group_attribute uniquemember; 41 | group_attribute_is_dn on; 42 | require valid_user; 43 | } 44 | 45 | server { 46 | listen 3443; 47 | 48 | ssl on; 49 | ssl_certificate /data/server.crt; 50 | ssl_certificate_key /data/server.key; 51 | 52 | location / { 53 | limit_except GET HEAD OPTIONS { 54 | auth_ldap "LDAP Authorization Request"; 55 | auth_ldap_servers ldap1; 56 | # auth_ldap_servers ldap2; 57 | } 58 | proxy_set_header X-Forwarded-Proto $scheme; 59 | proxy_set_header Host $http_host; 60 | proxy_set_header X-Real-IP $remote_addr; 61 | client_max_body_size 800M; # avoid HTTP 413 for large image uploads 62 | chunked_transfer_encoding on; # required to avoid HTTP 411: see Issue #1486 (https://github.com/dotcloud/docker/issues/1486) 63 | proxy_pass http://docker-registry; 64 | } 65 | } 66 | -------------------------------------------------------------------------------- /nginx/docker-registry.htpasswd: -------------------------------------------------------------------------------- 1 | testuser:$apr1$ocTQYcLD$BnXIF02GPcivTjrFQHXXg.:passwd 2 | larrycai:$apr1$xnWcsIpg$rorRDwNAB81VuuLiZspYK0:passwd -------------------------------------------------------------------------------- /nginx/nginx.conf: -------------------------------------------------------------------------------- 1 | user www-data; 2 | worker_rlimit_nofile 32768; 3 | pid /var/run/nginx.pid; 4 | 5 | events { 6 | worker_connections 8192; 7 | } 8 | 9 | http { 10 | 11 | ## 12 | # Basic Settings 13 | ## 14 | 15 | sendfile on; 16 | tcp_nopush on; 17 | tcp_nodelay on; 18 | keepalive_timeout 65; 19 | types_hash_max_size 2048; 20 | # server_tokens off; 21 | 22 | # server_names_hash_bucket_size 64; 23 | # server_name_in_redirect off; 24 | 25 | include /usr/local/nginx/conf/mime.types; 26 | default_type application/octet-stream; 27 | 28 | ## 29 | # Logging Settings 30 | ## 31 | 32 | access_log /dev/stdout; 33 | error_log /dev/stdout; 34 | 35 | ## 36 | # Gzip Settings 37 | ## 38 | 39 | gzip on; 40 | gzip_disable "msie6"; 41 | 42 | # gzip_vary on; 43 | # gzip_proxied any; 44 | # gzip_comp_level 6; 45 | # gzip_buffers 16 8k; 46 | # gzip_http_version 1.1; 47 | # gzip_types text/plain text/css application/json application/x-javascript text/xml application/xml application/xml+rss text/javascript; 48 | 49 | ## 50 | # nginx-naxsi config 51 | ## 52 | # Uncomment it if you installed nginx-naxsi 53 | ## 54 | 55 | #include /etc/nginx/naxsi_core.rules; 56 | 57 | ## 58 | # nginx-passenger config 59 | ## 60 | # Uncomment it if you installed nginx-passenger 61 | ## 62 | 63 | #passenger_root /usr; 64 | #passenger_ruby /usr/bin/ruby; 65 | 66 | ## 67 | # Virtual Host Configs 68 | ## 69 | 70 | include /usr/local/nginx/conf/conf.d/*.conf; 71 | include /usr/local/nginx/conf/docker-registry.default; 72 | } 73 | 74 | daemon off; 75 | -------------------------------------------------------------------------------- /nginx/server.crt: -------------------------------------------------------------------------------- 1 | -----BEGIN CERTIFICATE----- 2 | MIIC6TCCAdECAQIwDQYJKoZIhvcNAQELBQAwYzELMAkGA1UEBhMCQ04xCzAJBgNV 3 | BAgMAlNIMQswCQYDVQQHDAJTSDEhMB8GA1UECgwYSW50ZXJuZXQgV2lkZ2l0cyBQ 4 | dHkgTHRkMRcwFQYDVQQDDA5sYXJyeWNhaXl1LmNvbTAeFw0xNDExMjkwNjQxMzZa 5 | Fw0xNTExMjkwNjQxMzZaMBIxEDAOBgNVBAMMB2Rva2suY28wggEiMA0GCSqGSIb3 6 | DQEBAQUAA4IBDwAwggEKAoIBAQDNbDqsXXxjMVpHkHInl39cZP8kNbaDNJCk2uVP 7 | PDJ5aliVQgTGmIHPpJBiQJQ66uql/SX4tcAfZm1JoWPcmO/CnHYrLLL5f5u/JtEk 8 | 2B5E+n2yUC20RmWQ32nQeslkbbgmTVD/bb05jVLhUYaRzJ63bPGI4Wtj1icujS0F 9 | pIi0ism9YmZNOdGyETpFdZbL+ZU1ALMANgOlSfoaSWDtSCC3TyAolkY7GplJpdCp 10 | Xie+AQLUTP0EWAkaQ2CmndHGzZyLXu8fEErChf4QmYXYigvSoojj3+rPZJSNbLPv 11 | X+UKXqw22cjFj/3IG4WIQOTjH6BRgGDN/RZA3aW/ZcOs+3Y9AgMBAAEwDQYJKoZI 12 | hvcNAQELBQADggEBAMTUWoAYV68doOJx7AtKgoRwyJ89tDq79JvHyltwkEgFsKGJ 13 | YagtjKbAwb0Gio9RuSKz6JagayKFswv+Zu1yOx6cQkPuk+GgwNH+ArzdJJwuqKRW 14 | Qefbu3Os6Lt8tTdSzDjYirPWbrL4ne2UiSWaKKDFUi8IKZGtRWY0SZsk8xut/agA 15 | 686BcubAE0SuYzVbtOjczHUk/ykzs/QIXDZ2ja86mDcBXKviGHBFQ13Hq8XK0h24 16 | 0ASu9/h1te2vcTk+VEC1c/Z0ibztcPZC7r90jiZYVjNmuSlmwlHJ2+gFpOOzwEpr 17 | iBRNkHvX0lHTW9mVgo6pro3idyNBuiLQ2GVJXGg= 18 | -----END CERTIFICATE----- 19 | -------------------------------------------------------------------------------- /nginx/server.key: -------------------------------------------------------------------------------- 1 | -----BEGIN RSA PRIVATE KEY----- 2 | MIIEogIBAAKCAQEAzWw6rF18YzFaR5ByJ5d/XGT/JDW2gzSQpNrlTzwyeWpYlUIE 3 | xpiBz6SQYkCUOurqpf0l+LXAH2ZtSaFj3Jjvwpx2Kyyy+X+bvybRJNgeRPp9slAt 4 | tEZlkN9p0HrJZG24Jk1Q/229OY1S4VGGkcyet2zxiOFrY9YnLo0tBaSItIrJvWJm 5 | TTnRshE6RXWWy/mVNQCzADYDpUn6Gklg7Uggt08gKJZGOxqZSaXQqV4nvgEC1Ez9 6 | BFgJGkNgpp3Rxs2ci17vHxBKwoX+EJmF2IoL0qKI49/qz2SUjWyz71/lCl6sNtnI 7 | xY/9yBuFiEDk4x+gUYBgzf0WQN2lv2XDrPt2PQIDAQABAoIBAD94NjS1ec5IHGXK 8 | KoszEuXgSrjMY8TsQ9i7zWgK6Gl9Qztyt3kI++rFJNtGqsX9eVyp98Z9mYvaIOBE 9 | Hk+1bTcLErPKTs4p8FxCSRKCN/AGGToz7bsqmQ0HCnGgzoLaJ7Cl6OXS6UlT8gyu 10 | HM8FkvCHl6U8SOsC6v5GHmgE6zwkq9LHKkvhSNCI0nXivClhi/RtoVLooHQBnvFa 11 | /AWnUJgOdrdsqLI4sd2PzgubfU//eJdPcvC34L0vDB8NRABElmQkQhN8r5Eo6gSP 12 | bxXMjIEzEU3LJKpXMGaeL/O22RWvv12I8kC7fBWQ4Ezr647NTuWG+uUbRbatcjox 13 | Bc6N4v0CgYEA731h+WTyZhqsPATxE0XfitUTldp4Kp4WEDMZ28L32zxSv7dy/DnI 14 | YgUMXS3mktFzK27rr42vDLb+/xbr/w9kKs549aBZ088NpHH8HALYN05BqaPF8sRt 15 | bNcuS6dgrQL3De71m/EfMNmv+YUhl5u1DNoyGeV0CM8XZHLRUk1AqdcCgYEA25We 16 | E+PltaD095fTMCT46aSxz4CeAlYNwktKZ/2hXtyv544Iubd4hZkoRFH3o79lvofh 17 | mLXMrsyiHAaX57WFTNzjd/ZNVzuT0ficolGltvY+OZieiI3k4I/Qw3X+RfERQYs1 18 | jucNyTa5QAHn4h+x6M5AH+RmLIIH4k6ma7Cr5gsCgYBFX2SKAZvVx9QsbqIGmy7t 19 | 4FsUBXzZm4F4n9TVu9xgPVEbB+De/z30ZtH2C93GmbVq126eI8SZQkkLS3CBKcwy 20 | Oiz/ubtLh6bEA+CrnIdVPe33XeFxOUUZShu2/n0aoMk/2AB9c5M9a1F2TgI1EH2Z 21 | g3sP1U+PXa3BAyFvXcFlcQKBgBHGTbJ8eya1rb6xCoZWJ9P54e7TEXdM8fYtVAuQ 22 | 61Qbdx2+UJR/9oCSAkFthSc7IghHRYqwBK6Nn/22xusZtX2gT8VxKZeLGg8gGcXF 23 | 6C0kR6sv4H1bRxCqc5Ku5XNR7TyqAR7dMy97f4lf3h5exG786xHp0h9+MxctmKkU 24 | 9wU7AoGAeNksBz3OTCkP7ZH+8Vgtx/NaA0AHwQNg9ZsDZSVZjh+4W3Vyx9mMXQrO 25 | 5g+rdLorqTVBxPwQjgCNjMP99Jc9aV00HGRjP7l2ig8WAen4Nan9G5GqO4iL/N5a 26 | tiYoaitbkFsnFkdsezSWsFrHFa+YVx0XP7SKdik8TdE5q4dCjds= 27 | -----END RSA PRIVATE KEY----- 28 | -------------------------------------------------------------------------------- /start.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | NGINX=/usr/local/nginx 4 | DATA=/data 5 | 6 | cp /app/nginx/nginx.conf ${NGINX}/conf/nginx.conf 7 | cp /app/nginx/docker-registry.default ${NGINX}/conf/docker-registry.default 8 | 9 | if [ ! -f ${DATA}/server.crt ]; 10 | then 11 | echo "use default server certification for demo purpose !!" 12 | mkdir -p ${DATA} 13 | mkdir -p /conf 14 | cp /app/nginx/server.crt ${DATA}/ 15 | cp /app/nginx/server.key ${DATA}/ 16 | cp /app/nginx/docker-registry.htpasswd ${NGINX}/conf 17 | fi 18 | 19 | if [ ! -f ${DATA}/docker-registry.htpasswd ]; 20 | then 21 | echo "use default htpasswd for demo purpose !!" 22 | cp /app/nginx/docker-registry.htpasswd ${DATA} 23 | fi 24 | 25 | ${NGINX}/sbin/nginx 26 | --------------------------------------------------------------------------------