Skip to content
Snippets Groups Projects
Commit badb4abd authored by Quentin Duchemin's avatar Quentin Duchemin
Browse files

LDAP authentication with Docker registry

parent 38528360
No related branches found
No related tags found
1 merge request!68LDAP authentication with Docker registry
FROM debian:bullseye
ARG NGINX_VERSION=1.21.4
LABEL maintainer picasoft@assos.utc.fr
# Install prerequisites
RUN apt-get update && \
apt-get install -y build-essential git-core libpcre3-dev libldap2-dev libssl-dev wget zlib1g zlib1g-dev
# Download LDAP module
RUN git clone https://github.com/kvspb/nginx-auth-ldap.git /nginx-auth-ldap
# Download and build NGINX with LDAP module
RUN wget -O nginx.tar.gz http://nginx.org/download/nginx-${NGINX_VERSION}.tar.gz && \
tar xvf nginx.tar.gz && \
cd nginx-${NGINX_VERSION} && \
chmod +x configure && \
./configure --user=nginx --group=nginx --prefix=/etc/nginx --sbin-path=/usr/sbin/nginx --conf-path=/etc/nginx/nginx.conf --pid-path=/var/run/nginx.pid --lock-path=/var/run/nginx.lock --error-log-path=/var/log/nginx/error.log --http-log-path=/var/log/nginx/access.log --with-http_gzip_static_module --with-http_stub_status_module --with-http_ssl_module --with-pcre --with-file-aio --with-http_realip_module --add-module=/nginx-auth-ldap/ --with-ipv6 --with-debug && \
make && \
make install
COPY ./entrypoint.sh /entrypoint.sh
COPY ./nginx.conf /etc/nginx/templates/nginx.conf.template
RUN touch /etc/nginx/site.conf
RUN apt-get install -y gettext-base && \
chmod +x /entrypoint.sh
RUN useradd nginx
EXPOSE 80
ENTRYPOINT ["/entrypoint.sh"]
CMD ["nginx"]
## nginx with LDAP authentication
nginx has a mechanism allowing to use an external service handling authentication requests. For LDAP, the traditionnal way involves running a [ldap-auth](https://github.com/nginxinc/nginx-ldap-auth) daemon. It seemed a bit burdensome to me, even if there is a [Docker image](https://hub.docker.com/r/bitnami/nginx-ldap-auth-daemon/) for the daemon. I think this is because LDAP auth is included in NGINX Plus and a bit tricky to integrate with free pre-built packages.
There is an unofficial nginx module, [nginx-auth-ldap](https://github.com/kvspb/nginx-auth-ldap), which works well. We just need to recompile nginx with it, and voilà.
This is the purpose of this repository : make a ready-to-use nginx single image with LDAP auth.
## Sample usage with Compose
```yaml
version: '3.8'
services:
nginx_ldap:
image: registry.picasoft.net/pica-nginx-ldap:1.21.4
container_name: registry_frontend
environment:
LDAP_URL: ldaps://ldap.picasoft.net:636
LDAP_BASE_DN: dc=picasoft,dc=net
LDAP_ANSWER_ATTRIBUTES: cn
LDAP_SCOPE_SEARCH: sub
LDAP_FILTER: (objectClass=posixAccount)
LDAP_BIND_DN: cn=nss,dc=picasoft,dc=net
SERVER_NAME: registry.picasoft.net
ports:
- 8080:80
env_file: ./secrets/ldap.secrets
restart: unless-stopped
```
With `LDAP_BIND_PASSWORD=XXX` in `ldap.secrets`.
## Build
```
docker build -t nginx-ldap .
```
## LDAP configuration
Via Environments variables :
- `LDAP_URL``ldap[s]://<url>:<port>`
- `LDAP_BASE_DN` → where to start the search
- `LDAP_ANSWER_ATTRIBUTES` → which attributes to get back, comma-separated.
- `LDAP_SCOPE_SEARCH` : `base`, `one` or `sub`
- `LDAP_FILTER` : constrain the search
- `LDAP_BIND_DN` : user with read access
- `LDAP_BIND_PASSWORD` : password for the user with read access
See [official docs](https://ldapwiki.com/wiki/LDAP%20URL) for detail.
## Server configuration
Environment variable :
- `SERVER_NAME` : URL of your website.
Mount a file at `/etc/nginx/site.conf`. Every line will be included in the `server {}` section of `nginx.conf`.
Environment variables **won't be** subtituted at startup.
Note that nginx always listen internally on port 80. To change all configuration you can just mount an `nginx.conf` file. The moninal use is pretty standard : act as an authorization proxy or serve a simple single website.
#!/bin/sh
# Substitute env variables (secrets) in nginx configuration
envsubst < /etc/nginx/templates/nginx.conf.template > /etc/nginx/nginx.conf
# Execute initial command
exec $@
worker_processes 1;
daemon off;
error_log /dev/stdout info;
events {
worker_connections 1024;
}
http {
include mime.types;
default_type application/octet-stream;
access_log /dev/stdout;
sendfile on;
keepalive_timeout 65;
ldap_server main {
url ${LDAP_URL}/${LDAP_BASE_DN}?${LDAP_ANSWER_ATTRIBUTES}?${LDAP_SCOPE_SEARCH}?${LDAP_FILTER};
binddn ${LDAP_BIND_DN};
binddn_passwd ${LDAP_BIND_PASSWORD};
require valid_user;
}
server {
listen 80;
server_name ${SERVER_NAME};
auth_ldap "Enter LDAP credentials";
auth_ldap_servers main;
include /etc/nginx/site.conf;
}
}
LDAP_PASSWORD=test
pica:<encrypted_password>
......@@ -3,6 +3,8 @@ version: '3.7'
networks:
proxy:
external: true
registry:
name: registry
volumes:
registry:
......@@ -13,18 +15,35 @@ services:
image: registry:2
container_name: registry
environment:
REGISTRY_AUTH: htpasswd
REGISTRY_AUTH_HTPASSWD_PATH: /auth/htpasswd
REGISTRY_AUTH_HTPASSWD_REALM: Registry Realm
REGISTRY_STORAGE_FILESYSTEM_ROOTDIRECTORY: /var/lib/registry
REGISTRY_HTTP_HOST: registry.picasoft.net
networks:
- proxy
- registry
volumes:
- registry:/var/lib/registry
- ./auth.secrets:/auth/htpasswd
restart: unless-stopped
nginx_ldap:
image: registry.picasoft.net/pica-nginx-ldap:1.21.4
build: ../pica-nginx-ldap
container_name: registry_frontend
environment:
LDAP_URL: ldaps://ldap.picasoft.net:636
LDAP_BASE_DN: dc=picasoft,dc=net
LDAP_ANSWER_ATTRIBUTES: cn
LDAP_SCOPE_SEARCH: sub
LDAP_FILTER: (objectClass=posixAccount)
LDAP_BIND_DN: cn=nss,dc=picasoft,dc=net
SERVER_NAME: registry.picasoft.net
env_file: ./secrets/ldap.secrets
volumes:
- ./proxy.conf:/etc/nginx/site.conf
labels:
traefik.http.routers.registry.entrypoints: websecure
traefik.http.routers.registry.rule: Host(`registry.picasoft.net`)
traefik.http.services.registry.loadbalancer.server.port: 5000
traefik.http.services.registry.loadbalancer.server.port: 80
traefik.enable: true
networks:
- registry
- proxy
restart: unless-stopped
# disable any limits to avoid HTTP 413 for large image uploads
client_max_body_size 0;
# required to avoid HTTP 411: see Issue #1486 (https://github.com/moby/moby/issues/1486)
chunked_transfer_encoding on;
location /v2 {
add_header 'Docker-Distribution-Api-Version' 'registry/2.0';
proxy_pass http://registry:5000;
proxy_set_header Host $http_host; # required for docker client's sake
proxy_set_header X-Real-IP $remote_addr; # pass on real client's IP
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
# Forwarding from Traefik, always https
proxy_set_header X-Forwarded-Proto https;
proxy_read_timeout 900;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection keep-alive;
proxy_request_buffering off;
proxy_cache off;
proxy_buffering off;
}
LDAP_BIND_PASSWORD=test
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment