LDAP avec deux domaines (dans une Jail)

Un problème nouveau c’est fait jour récement en raison des organisations différentes que je gère sur mon serveur. J’ai un serveur LDAP dans lequel j’ai, à l’arrache, mis les utilisateurs de ma propre organisation example.com et ceux d’une autre organisation, Exodus Privacy.

Tout fonctionnait à merveille jusqu’au jour ou nous avons décidé, chez Exdus Privacy, d’avoir des services spécifiques pour gérer notre activité. La mise en place d’un helpdesk, d’un erp (je vous en reparlerais plus tard sans doute).

Il était donc temps de séparer les deux organisations dans le LDAP.

  Des notions importantes de LDAP doivent être acquises avant d’aller plus loin. Lisez par exemple le vieux billet sur la mise en place de LDAP sur FreeBSD.

  Je n’ai pas réussi à passer à la « nouvelle » façon de gérer les entrées LDAP, j’en suis resté au bon vieux fichier slapd.conf(5)1.

  Ce que je vais réaliser ici est une migration. Toutefois le principe reste le même pour une création. Dans ce cas vous pouvez passer directement à Préparation de la jail cible

  Comme toujours quand je parle de jail, on suppose que celle-ci est prête et dispose d’un accès réseau.

Sauvegarde de l’ancienne base

Pour sauvegarder l’ancienne base rien de plus simple, l’outil slapcat(8C) est fait pour cela :

 # slapcat > ldap.bak.ldif

Le résultat est au format LDIF, qui est assez compréhensible pour un être humain.

Nettoyage du fichier LDIF

Nous allons immédiatement nettoyer ce fichier de tous les champs qui n’ont plus lieu d’être renseigné. Parmi eux on trouve le timestamp de la création de l’entrée (qui va forcément changer à l’import).

Nous allons pour cela utiliser un autre fichier LDIF et la commande sed(1).

1
2
3
4
5
6
7
 /^creatorsName: /d
 /^createTimestamp: /d
 /^modifiersName: /d
 /^modifyTimestamp: /d
 /^structuralObjectClass: /d
 /^entryUUID: /d
 /^entryCSN: /d

Nommons ce fichier cleanner.ldif.

Et le nettoyage est simple (encore une beauté Unix) :

 # cat ldap.bak.ldif | sed -f cleanner.ldif > ldap-clean.ldif

Division des deux arbres

Là, je ne pourrais rien pour vous pour automatiser cette partie. Vous n’avez qu’à espérer que votre fichier ldap-clean.ldif est suffisament cohérent pour retrouver les enregistrements des deux arbres.

Début des fichiers séparés

Une fois vos fichiers séparés (dans mon cas en exemple.com.ldif et exodus.ldif), il faut s’assurer que les premiers enregistrements, obligatoires, sont bien présents. Ce sont ceux de la mise en place de la structure de la base 

 dn: dc=example,dc=com
 dc: example
 objectClass: dcObject
 objectClass: organization
 o: example
 
 dn: ou=people,dc=example,dc=com
 ou: people
 objectClass: organizationalUnit
 
 dn: ou=groups,dc=example,dc=com
 ou: groups
 objectClass: organizationalUnit

Le premier paragraphe créé la racine de l’arbre, le deuxième, l’unité d’organisation people et le troisième l’unité d’organisation groups.

Ces enregistement sont à reproduire au dépuis de chaque fichier de données LDIF. En adaptant selon votre cas réel.

Suivent les enregistrements des objets de la base existants, des groups et des people.

Préparation de la jail cible

Sur cette machine nous auront besoin de openldap24-server, openldap24-client et de nss_pam_ldap.

Configuration du démon slapd

Cela se fait dan le fichier /usr/loca/etc/openldap/slapd.conf. Nous allons y définir les options générales au démon puis les options spécifiques à chacune des bases et donc chacun des arbres.

Considération d’ordre générale dans la configuration

Nous allons tout d’abord importer les fichiers de schéma dont nous avons besoin (si vous faites une migration, cette section est la même que pour votre serveur actuel).2

1
2
3
4
5
6
7
 include         /usr/local/etc/openldap/schema/core.schema
 include         /usr/local/etc/openldap/schema/cosine.schema
 include         /usr/local/etc/openldap/schema/corba.schema
 include         /usr/local/etc/openldap/schema/inetorgperson.schema
 include         /usr/local/etc/openldap/schema/nis.schema
 include         /usr/local/etc/openldap/schema/collective.schema
 include         /usr/local/etc/openldap/schema/openldap.schema


Configuration du chemin et du niveau de trace et autres babiolles

On configure les differents chemins et niveau de trace du démon slapd :

1
2
3
4
 pidfile         /var/run/openldap/slapd.pid
 argsfile        /var/run/openldap/slapd.args
 logfile         /var/log/slapd.log
 loglevel        256

Et les modules à charger en mémoire au démarrage :

1
2
3
4
 # Load dynamic backend modules:
 modulepath      /usr/local/libexec/openldap
 moduleload      back_mdb
 moduleload      back_ldap

Viennent ensuite les ACL3

1
2
3
4
 access to *
        by self write
        by users read
        by anonymous auth

  Reportez-vous à la documentation officielle pour comprendre les tenants et aboutissants de vos choix.

Configuration de chacune des bases, une par domaine

Cette configuration est propre à chaque arbre (ou domaine) et devra donc être répétée avec les changements qui s’imposent :

 database        mdb
 maxsize         1073741824
 suffix          "dc=example,dc=com"
 rootdn          "cn=admin,dc=example,dc=com"
 # Cleartext passwords, especially for the rootdn, should
 # be avoid.  See slappasswd(8) and slapd.conf(5) for details.
 # Use of strong authentication encouraged.
 rootpw
 {SSHA}fefjdhkjhkoewqirklkjfkdsjfdsfefjdhkjhkoewqirklkjfkdsjfds
 # The database directory MUST exist prior to running slapd AND
 # should only be accessible by the slapd and slap tools.
 # Mode 700 recommended.
 directory       /var/db/openldap-data/example
 # Indices to maintain
 index   cn,sn,uid pres,eq,approx,sub
 index   objectClass     eq

  Pour obtenir le hash du mot de passe il faut utiliser le programme slappasswd(8) :

 # slappasswd 
 New password: 
 Re-enter new password: 
 {SSHA}enK5mLVqjZPnUlJb2X/irdL95DK/wUjS

Dėmarrage de slapd

Avant de peupler nos arbres avec les données des fichiers LDIF, il est nécessaire de démmarrer une première fois slapd(8C) pour que ce dernier créé les base de données correspondantes.

On commence par mettre le démarrage du démon au lancement de la jail, et on le démarre :

 # sysrc slapd_enable="YES"
 # service slapd start 

Import des données

Nous pouvons utiliser deux méthodes pour l’import des données. La méthode online, avec le démon lancé ou la méthode offline, démon arrêté avec d’autres commandes.

Import online

Notre démon slapd(8C) tourne, nous allons utiliser la commande ldapadd(1) pour importer les données :

 # ldapadd -vv -f example.com.ldif -x -D"cn=admin,dc=example,dc=com" -w motDePasse

et :

 # ldapadd -vv -f exodus.ldif -x -D"cn=admin,dc=exodus-privacy,dc=eu.org" -w OhMonBateau

Import offline

Pour faire l’import offline, on commence par arrêter le démon slapd(8C) :

 # service slapd stop

Et on utilise la commande slapadd :

 # slapdadd -l /tmp/example.com.ldif -f /usr/local/etc/openldap/slapd.conf -b "dc=example,dc=com"

Et bien sût l’équivalent pour l’autre arbre :

 # slapdadd -l /tmp/exodus.ldif -f /usr/local/etc/openldap/slapd.conf -b "dc=exodus-privacy,dc=eu.org"

Accéder aux données

Pour accéder aux données de nos bases nous allons avoir besoin de nss-pam-ldapd et de modifier le fichier /etc/nsswitch.conf.

Le fichier /etc/nsswitch.conf

Ce fichier indique dans quel ordre doivent être recherchés certaines informations, comme les comptes utilisateurs, les adresses de machines, etc.

Le nôtre doit ressembler à cela pour indiquer que les groupes et comptes utilisateurs doivent être recherchés d’abord dans les fichiers locaux, puis dans la base LDAP :

 passwd: files ldap
 group: files ldap

Le paquet nss_pam_ldapd et son fichier de configuration

Le fichier de configuration est /usr/local/etc/nslcd.conf et est, dans son utilisation la plus simple, très facile à mettre en place.

On indique simplement l’URI de connexion au serveur LDAP (ici 127.0.0.1) et les deux bases dans lesquels chercher les objets.

 uri ldap://127.0.0.1/

 # The LDAP version to use (defaults to 3
 # if supported by client library)
 #ldap_version 3

 # The distinguished name of the search base.
 base dc=example,dc=com
 base dc=exodus-privacy,dc=eu.org

Lancement au démarrage de la jail

Comme tous les démons que nous utilisons il est nécessaire de faire en sorte que celui-ci soit lancé au démarrage de la jail :

 # sysrc nslcd_enable="YES"
 # nslcd start

Vérification

Il nous reste à vérifier que notre serveur LDAP répond correctement. L’utilitaire getent(8) va nous aider :

 # getent passwd

Si vous avez comme résultat la liste des utilisateurs des deux domaines, c’est gagné, vous pouvez maintenant vous servir de votre serveur LDAP en interrogeant tantôt une base dans tantôt une autre selon le contexte.

Conclusion

Au prix de peu d’effort (mis à part le nettoyage du fichier issu de slapcat(8C)), nous avons fait le ménage dans les arbres des deux domaines ayant par la même une gestion plus rationnelle tout en n’ayant qu’un seul serveur LDAP. Il est bien sûr possible de mettre en place des répliques et je vous laisse le soin de penser aux sauvegardes de vos deux arbres4.


  1. Elle a tout de même plus de 10 ans [return]
  2. Les schémas décrivent comment les données doivent être intégrées dans la base, si elles sont uniques ou pas, le type de données, etc. [return]
  3. Access Control List, les liste de contrôle d’accès [return]
  4. Ce que nous venons de voir pour deux arbres doit pouvoir s’appliquer à plus. [return]