Présentation de LDAP

LDAP fournit un ensemble d'outils.

  1. un protocole permettant d'accéder à l'information contenue dans l'annuaire,

  2. un modèle d'information définissant l'organisation et le type des données contenues dans l'annuaire,

  3. un modèle de nommage définissant comment l'information est organisée et référencée

  4. un modèle fonctionnel qui définit comment accéder à l'information,

  5. un modèle de sécurité qui définit comment accéder aux données et comment celles-ci sont protégées. OpenLDAP est souvent configuré avec SASL (Simple Authentication and Security Layer), qui permet les transactions cryptées avec les protocoles fonctionnant en mode connecté.

  6. un modèle de duplication qui définit comment la base est répartie entre serveurs,

  7. des APIs pour développer des applications clientes,

  8. LDIF, (Ldap Data Interchange Format) un format d'échange de données.

Le protocole

Un protocole d'accès aux données, qui décrit comment ajouter, modifier, supprimer des données dans la base de donnée, quels protocoles de chiffrement (kerberos, ssl...), et quels mécanismes d'authentification sont utilisés. Ce protocole est utilisé dans la relation client/serveur, mais également entre serveurs (serveur/serveur) car une base de données LDAP peut être répartie.

Le modèle de données

Le Directory Information Tree

LDAP fournit un modèle d'organisation des données. Ces données sont organisées sous forme hiérarchique. L'arbre est nommé Directory Information Tree (DIT). Le sommet (racine), contient le "suffixe". Chaque noeud représente une "entrée" ou "Directory Entry Service" (DSE). Les données sont stockées sur un format de base de données hiérarchique de type "dbm". Ce format est différent des bases de données relationnelles, conçues pour supporter de multiples mises à jour. DBM est conçu pour supporter peu de mises à jour, mais de nombreuses consultations.

Figure 51.1. LDAP : le DIT Directory Information Tree

LDAP : le DIT Directory Information Tree

Classes d'objets, objets, attributs et schéma

Une entrée (DSE) dnas le DIT correspond à un objet abstrait (organisation, ressource) ou concret (personne, équipement...). Les objets possèdent une description dans une "classe d'objet". Une classe d'objet donne une représentation modélisée des objets qu'elle représente en caractérisant tous les attributs des objets.

Certaines classes dobjet ont fait l'objet d'une normalisation et sont réutilisables. Elles sont définies par un nom, un OID (Object Identifier), la liste des attributs (facultatifs ou obligatoires), et, pour chaque attribut, un type. Le type est lié à la nature (essentiellement texte ou binaire) des attributs utilisés.

Une classe d'objet est définie par un nom, un OID (Object IDentifier), la liste des attributs (facultatifs et obligatoires), un type. Le type est lié à la nature des attributs utilisés.

Chaque objet est composé d'attributs en fonction des types d'attributs décrits dans les classes d'objets. Un attribut est généralement un couple clé/valeur, mais peut être caractérisé par un nom, un OID, s'il est mono ou multi-évalué, un indicateur d'usage (facultatif/obligatoire), un format (voir par exemple pour les images).

Les OID sont normalisés par la RFC2256 et sont issus d'un schéma X500. Les OID sont tenus à jour par l'IANA Internet Assigned Numbers Authority. Un OID est une séquence de chiffres séparés par un "." point (Exemple 1.2.3.4 ) qui permet d'identifier de façon unique un élément du schéma LDAP.

Exemple de la la classe inetOrgPerson (dépend de organizationalPerson)

# The inetOrgPerson represents people who are associated with an
# organization in some way.  It is a structural class and is derived
# from the organizationalPerson which is defined in X.521 [X521].
Objectclass     ( 2.16.840.1.113730.3.2.2  <-------------- OID
  NAME 'inetOrgPerson'
     DESC 'RFC2798: Internet Organizational Person'
     SUP organizationalPerson
       STRUCTURAL
       MAY (
		audio $ businessCategory $ carLicense $ departmentNumber $
		displayName $ employeeNumber $ employeeType $ givenName $
		homePhone $ homePostalAddress $ initials $ jpegPhoto $
		labeledURI $ mail $ manager $ mobile $ o $ pager $
		photo $ roomNumber $ secretary $ uid $ userCertificate $
		x500uniqueIdentifier $ preferredLanguage $
		userSMIMECertificate $ userPKCS12 )
	)

et l'attibut employeeType
# employeeType
# Used to identify the employer to employee relationship.  Typical values
# used will be "Contractor", "Employee", "Intern", "Temp", "External", and
# "Unknown" but any value may be used.
Attributetype ( 2.16.840.1.113730.3.1.4	
	NAME 'employeeType'
	DESC 'RFC2798: type of employment for a person'
	EQUALITY caseIgnoreMatch
	SUBSTR caseIgnoreSubstringsMatch
	SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 )
Signification des mots réservés :

DESC : 	Description 
SUP : 		Objet parent
MUST : 	Attributs requis
MAY : 	Attributs possibles

Chaque objet de l'annuaire qui correspond à une classe d'objet est décrit par des valeurs en fonction des attributs qui décrivent la classe d'objets. Un attribut est généralement un couple clé/valeur, mais peut être caractérisé par un nom, un OID, indique s'il est mono ou multi-évalué, donne un indicateur d'usage (facultatif/obligatoire), impose un format (par exemple base64 pour les images, utf-8 pour les données).

Les objets sont rattachés obligatoirement à au moins une classe d'objet. Une classe d'objet caractérise ou modélise les objets qui lui seront rattachés. On en déduit qu'un objet ne pourra pas avoir d'attribut non déclaré dans la classe d'objet. Par contre dans la classe d'objet, un attribut pourra être soit optionnel, soit obligatoire. L'administrateur a déjà des classes d'objets prédéfinies, il a la possibilité d'en définir d'autres.

Chaque objet hérite des attributs des objets dont il hérite. Quand on décrit un objet "fils", on doit décrire tous les liens de parenté avec l'attribut "ObjetClass". Les objets forment une hiérarchie, avec, au sommet, l'objet "top". Exemple pour enrichir l'objet "person" des attributs "technicalPerson".

objectClass: top
objectClass: myOrganization
objectClass: person
objectClass: technicalPerson

L'ensemble de la description des classes d'objet et des types d'attributs définissent le "schéma".

Une entrée peut appartenir à plusieurs classes d'objets. Les attributs de l'objets sont la réunion des attributs de toutes les classes d'objets :

Entry Type        Required Attributes   Optional Attributes
person            commonName (cn)       mail
                  surName (sn)          mobile
                  objectClass           ...

OrganizationUnit  ou                    description
                  objectClass           localisation
                                        ...
Organization      o                     description
                  onjectClass           ...

Les OID sont normalisés par la RFC2256 et sont issus d'un schéma X55. Les OID sont tenus à jour par l'IANA Internet Assigned Numbers Authority. Un OID est une séquence de chiffres séparés par un "." point. Exemple 1.2.3.4

Le "dn", ou Distinguished Name, est le chemin absolu de l'entrée dans le DIT à partir de la racine. Par exemple :

dc=org, dc=mydomaine, ou=person, uid=toor

On peut utiliser aussi un nommage "relatif" par rapport à une position courante. Dans ce cas on utilise le RDN (Relative Distinguished Name).

Le format d'échange de donnée LDIF

Le format d'échange permet l'import/export de données des bases, mais sert également pour l'ajout ou la modification. Les données sont en ASCII codées en UTF-8, sauf pour le binaire qui est codé en base64 (images par exemple).

Les fichiers au format LDIF respectent une structure de description des objets et des commandes :

Syntaxe générale :
    dn: <distinguished name 
    objectClass: <object class 
    objectClass: <object class 
    ... 
    <attribute type:<attribute value 
    <attribute type:<attribute value 
    ...

Exemple :
    dn: cn= Manon Des Sources, ou= compta, dc=mydomain, dc=org
    objectClass: person
    objectClass: organization
    cn: AN GROSSI
    sn: GROSSI
    givenName: AM
    userPassword: {sha}KDIE3AL9DK
    uid: amg

Les fichiers supportent également des commandes pour ajouter, modifier ou supprimer une entrée.

    dn: distinguished name
    changetype <identifier
    change operation identifier
    list of attributes...
    ...
    -
    change operation identifier
    list of attributes
    ...
    <identifier : 
        add (ajouter une entrée,
        delete (suppression), 
        modrdn (modification du RDN), 
        modify (modification : add, replace, delete d'un attribut)

On utilise le caractère "-" pour séparer 2 instructions. Par exemple :

     dn: cn= Morina Fuentes, ou=admin, dc=mydomain, dc=org
     changetype: modify 
     add: telephonenumber
     telephonenumber: 05 55 55 55 55
     -
     add: manager
     manager: cn= toor root, ou=admin, dc=mydomain, dc=org

Les méthodes d'accès

Les opérations de base sont résumées ici :

Opération        
Search             recherche dans l'annuaire d'objets
Compare            comparaison du contenu de deux objets
Add                ajout d'une entrée
Modify             modification du contenu d'une entrée
Delete             suppression d'un objet
Rename (Modify DN) modification du DN d'une entrée
Bind               connexion au serveur
Unbind             deconnexion

Les requêtes de type "search" ou "compare" reçoivent des paramètres.


Paramètre
base object        l'endroit de l'arbre où doit commencer la recherche
scope              la profondeur de la recherche
size limit         nombre de réponses limite
time limit         temps maxi alloué pour la recherche
attrOnly           renvoie ou pas la valeur des attributs en plus de leur type
search filter      le filtre de recherche
list of attributes la liste des attributs que l'on souhaite connaître

Le scope (Profondeur de recherche)

Le scope définit la profondeur de la recherche dans l'arbre des données. La figure montre la portée d'une recherche ou d'une comparaison en fonction du paramètre scope.

search scope=base recherche uniquement dans l'entrée définie 
search scope=one recherche dans l'entrée définie et le premier sous-niveau
search scope = subtree, cherche dans toute la sous-arborescence. 

Figure 51.2. LDAP : ls scope

LDAP : ls scope

search scope=base recherche uniquement dans l'entrée définie

search scope=onelever search, cherche dans tous les noeuds fils rattachés directement au noeud courant

search scope = subtree, cherche dans toute la sous-arborescence.

Les URL LDAP offrent aux client web un accès aux bases de données :

ldap[s]://<hostname>:<port>/<base_dn>?\
          <attributes>?<scope>?<filter>

          <base_dn>   : DN de l'entrée qui est le 
                              point de départ de la recherche
          <attributes>: les attributs que l'on veut consulter
          <scope>     : la profondeur de recherche dans le 
                              DIT à partir du
          <base_dn>   :"base" | "one" | "sub"
          <filter>    : filtre de recherche, 
                              par défaut (objectClass=*)

Exemples :
    ldap://ldap.netscape.com/ou=Sales,o=Netscape,c=US?cn,\
           tel,mail?scope=sub?(objetclass=person)
    ldap://ldap.point-libre.org/cn=Manon,ou=Contact,o=point-libre.org

Le langage de commande

  1. - slapadd, slapcat, slapindex, slappasswd, fournis avec les serveurs LDAP (utilisables sous le compte root).

  2. - ldapadd, ldapdelete, ldapmodify, ldapmodrdn, ldappasswd, ldapsearch, fournis avec les utilitaires ldap (utilisable par les utilisateurs et les applications). Ils sont fournis par le paquet (ldap-utils)

Exemple :

ldapsearch  -x -h localhost -b "dc=mydomain,dc=fr" "objectclass=*"

Recherche de tous les objets sur l'annuaire de la machine locale, à partir de la racine. (-b indique à partir de quel niveau la recherche doit être exécutée). L'option « -x » indique de ne pas utiliser la méthode d'authentification SASL si elle n'est pas activée.

ldapdelete 'cn=Jean Colombani,cn=mydomain,cn=fr'

Suppression d'une entrée dans l'annuaire

ldapadd -f /tmp/unFichierAuFormatLDIF

Ajout dans l'annuaire à partir d'un fichier contenant des données au format LDIF.

Note: Pour éviter d'avoir à préciser à chaque fois certains paramètres (machine, port, annuaire...) il est possible de configurer le fichier de configuration « ldap.conf » qui sera utilisé par les applications clientes.