How to setup lightweight LDAP Server with docker

15 February 2022

6 min read

Share
blog Image
Author

This blog aims to build an LDAP Server with docker and docker-compose. This setup serves a useful purpose to deploy a temporary LDAP server for poc’s and testing our Microservices. Lightweight directory access protocol (LDAP) is a protocol that is used to by applications to query user information. It’s the most common way of user management by enterprise customers across the globe. I have been using this setup for testing infra setups and to test local app development.

LDAP server can be installed in windows server with it’s AD functionality or Linux with Samba util or can be custom built with ldap binary. This project uses the ldap binary packaged in the docker image with the minimum required addons to support the containerised server.

This project uses the openldap image from https://github.com/osixia/docker-openldap.git

Features of this setup

  • Lightweight LDAP server
  • Environment variables to manage mandatory ldap params
  • Access to LDAP Server in insecure and secure way
  • Add/modify the user and groups in server
  • Console to manage LDAP server
  • Image versions
    • osixia/openldap:1.5.0
    • osixia/phpldapadmin:0.9.0
  • Ldapserver can also be run individually as container

Resources for this setup is maintained at https://github.com/rajks24/ldapserver.git

Prepare workstation to access ldap server

As part of preparation , we can install openldap client in external VM. This can be used to access the LDAP server which we would be building with docker in the next section.

Below mentioned biraries prepare the linux vm with openldap client.

sudo yum install -y openldap openldap-clients openldap-servers

To get ldapserver cacert either we can copy from launched container, or use the extracted cacert from this repo

docker exec ldapserver cat /container/service/:ssl-tools/assets/default-ca/default-ca.pem > ldapca.crt

To enable external VM to secure access, need to add the ldapca.crt in /etc/openldap/ldap.conf and it’s corresponding parameter to check certs

TLS_CACERT /home/user1/certs/ldapca.crt
TLS_REQCERT     demand

✍️ NOTE: To disable use of SSL for an insecure access, we can set variable export LDAPTLS_REQCERT=never in external VM.

Access ldap server with ldapclient

To access LDAP server externally in a linux server configured with openldap-clients.

# insecure access
$ ldapsearch -x -b "dc=txvlab,dc=local" -H ldap://ldapserver:389 -D "cn=user-ro,dc=txvlab,dc=local" -w pass123
 
# secure access
$ ldapsearch -x -b "dc=txvlab,dc=local" -H ldaps://ldapserver:636 -D "cn=user-ro,dc=txvlab,dc=local" -w pass123

Docker Compose configure & run

version: '3.7'
services:
  openldap:
    image: osixia/openldap:1.5.0
    command: "--loglevel info"
    container_name: ldapserver
    hostname: ldapserver
    ports:
      - "389:389"
      - "636:636"
    volumes:
      - ./data/slapd/database:/var/lib/ldap
      - ./data/slapd/config:/etc/ldap/slapd.d
      - ./data/certificates:/container/service/slapd/assets/certs
      - ./ldifs:/openldap/ldif  
    environment:
      - LDAP_ORGANISATION=txvlab
      - LDAP_DOMAIN=txvlab.local
      - LDAP_ADMIN_USERNAME=admin
      - LDAP_ADMIN_PASSWORD=pass123
      - LDAP_CONFIG_PASSWORD=pass123
      - "LDAP_BASE_DN=dc=txvlab,dc=local"
      - LDAP_TLS_CRT_FILENAME=server.crt
      - LDAP_TLS_KEY_FILENAME=server.key
      - LDAP_TLS_CA_CRT_FILENAME=ldapcacert.crt
      - LDAP_TLS_VERIFY_CLIENT=try  
      - LDAP_READONLY_USER=true
      - LDAP_READONLY_USER_USERNAME=user-ro
      - LDAP_READONLY_USER_PASSWORD=pass123
      - LDAP_SEED_INTERNAL_LDIF_PATH=/openldap/ldif
    networks:
      - openldap
 
  phpldapadmin:
    image: osixia/phpldapadmin:0.9.0
    container_name: phpldapadmin
    hostname: phpldapadmin
    ports:
      - "8000:80"
    environment:
      - PHPLDAPADMIN_LDAP_HOSTS=ldapserver
      - PHPLDAPADMIN_HTTPS=false
    depends_on:
      - openldap
    networks:
      - openldap
 
networks:
  openldap:
    driver: bridge
  • The addition of the volumes with /data in the current location is an optional setup.
  • Hostname for openldap container and the PHPLDAPADMIN_LDAP_HOSTS variable for phpldapadmin console can be flexibly configured to match the hostname and/or domiain-name for the host VM in which this dockerised setup is configured. We may add entry in /etc/hosts for server-ip ldapserver
  • log label can be configured as info/debug based on the need and serves to expose the server’s behaviour and params.

To kickoff the server, need to use docker-compose up -d for it’s standalone run, and for poc troubleshooting purpose, we can run it without the “-d” option to access container flow logs.

The phpldapadmin container has dependency on the openldap container, so the startup may take some time ( in some occasions). Once the ldap server is running successfully , we would see the below logs in the openldap server container logs

ldapserver      | ***  INFO   | 2022-02-15 03:46:18 | Running /container/run/process/slapd/run...
ldapserver      | ***  DEBUG  | 2022-02-15 03:46:18 | /container/run/process/slapd/run started as PID 563
ldapserver      | 620b220a @(#) $OpenLDAP: slapd 2.4.57+dfsg-1~bpo10+1 (Jan 30 2021 06:59:51) $
ldapserver      | Debian OpenLDAP Maintainers <pkg-openldap-devel@lists.alioth.debian.org>
ldapserver      | 620b220a slapd starting

If we have launched the docker-compose setup with /datavolume mount to container, then we must delete the data folder, before relaunching the server again otherwise, the server crashes to launch.

Environment Variables

Below environment variables are configured in the current setup. We can refer to all the configurable variables here.

LDAP_ORGANISATION=txvlab
LDAP_DOMAIN=txvlab.local
LDAP_ADMIN_USERNAME=admin
LDAP_ADMIN_PASSWORD=pass123
LDAP_CONFIG_PASSWORD=pass123
"LDAP_BASE_DN=dc=txvlab,dc=local"
LDAP_TLS_CRT_FILENAME=server.crt
LDAP_TLS_KEY_FILENAME=server.key
LDAP_TLS_CA_CRT_FILENAME=ldapcacert.crt
LDAP_TLS_VERIFY_CLIENT=try
LDAP_READONLY_USER=true
LDAP_READONLY_USER_USERNAME=user-ro
LDAP_READONLY_USER_PASSWORD=pass123
LDAP_SEED_INTERNAL_LDIF_PATH=/openldap/ldif
cardIconNOTE

We can provide LDAP user and group in ldif format via the volume mounted to the container and integrated via the LDAP_SEED_INTERNAL_LDIF_PATH env variable To enable debugging in openldap server, we can use the command command: "--loglevel debug"

Exposed ports

ItemPort
LDAP access389
LDAPS access636
phpldapadmin console8000

Access phpldapadmin console

ItemDetails
Console URLhttp://ldapserver.txvlab.local:8000
usernamecn=admin,dc=txvlab,dc=local
passwordpass123

This console is very useful to access the server users/group setup and also it can be modified as per requirement multiple time as we get admin access to the server via the console. I have shared a set of user and groups in ldapusers.ldif for reference along with project resources.

ldapserver-admin-gui.jpg

Access ldap server with docker

The server is packed with the environment variables and the users/groups from the ldif/myusers.ldif into a docker image – ghcr.io/rajks24/ldapserver:1.0. We can access the image with docker and use the ldap server in poc’s.

$ docker pull ghcr.io/rajks24/ldapserver:1.0
1.0: Pulling from rajks24/ldapserver
433ab23181ef: Pull complete
Digest: sha256:a6e702120b8c506f9df3829da8f0ff933de10621eb19d81f8276b4a7c0115cad
Status: Downloaded newer image for ghcr.io/rajks24/ldapserver:1.0
ghcr.io/rajks24/ldapserver:1.0
 
$ docker run -d --rm --name ldapserver -p 389:389 -p 636:636 ghcr.io/rajks24/ldapserver:1.0
$ ldapsearch -x -b "dc=txvlab,dc=local" -H ldaps://ldapserver:636 -D "cn=user-ro,dc=txvlab,dc=local" -w pass123
cardIconNOTE

For secure access, we can use the cacert from repo or copy from running container from /container/service/:ssl-tools/assets/default-ca/default-ca.pem. Also we can configure in /etc/openldap/ldap.conf.

TLS_CACERT /root/ldapserver/certs/ldapca.crt
TLS_REQCERT demand

Troubleshooting

As the LDAP server is running within container, but to access externally, the hostname or domainname for host would be used. Thus, need to ensure that the hostname or domain-name of VM should be resolvable to ldapserver. It’s also important as the LDAP server cert configures the common-name(CN) to the ldapserver.