{{indexmenu_n>1}} # Structure et clarification du LDAP Cette page présente la structure de l'annuaire LDAP. Techniquement, cette structure se retrouve [ici](https://gitlab.utc.fr/picasoft/projets/services/openldap/-/tree/master/bootstrap). Cette page tente d'expliquer le pourquoi du comment du LDAP. Pour créer des utilisateurs ou des services et avoir plus de détails, consultez les pages dédiées du wiki. ## Introduction Une des difficultés de LDAP, à mon sens, est de comprendre ce qu'il fait et ne fait pas. LDAP est basiquement un **annuaire arborescent d'entrées**. On peut faire la comparaison avec un système de fichiers, où chaque répertoire peut contenir des répertoires ou des fichiers. Ici, chaque entrée peut contenir d'autres entrées. Chaque entrée se compose d'attributs. Chaque attribut a un nom et une ou plusieurs valeurs. Les attributs sont définis au sein de schémas. La plupart des schémas utiles sont déjà connus des serveurs LDAP, comme OpenLDAP. Les attributs sont regroupés au sein de classes. Les entrées ont donc des classes, qui indiquent les attributs qu'elles peuvent utiliser, s'ils sont obligatoire, quel est leur format, etc. Chaque entrée a un DN (`Distinguished Name`) qui permet de l'identifier de manière unique dans l'annuaire : c'est l'équivalent du chemin absolu dans un système de fichier. Il a aussi un RDN `Relative Distinguished Name`, qui est l'équivalent du nom d'un fichier ou d'un répertoire. Pris dans son ensemble, un annuaire LDAP **ne fait rien**. Ce n'est pas parce qu'on indique avec des attributs LDAP qu'un utilisateur a le droit de se connecter à `pica02` qu'il pourra le faire. C'est ensuite aux **clients** de l'annuaire de regarder le bon attribut, de l'interpréter et de donner l'autorisation. En gros, l'ajout d'attributs dans le LDAP ne change rien si le client n'a pas été paramétré pour prendre en compte ces attributs. On pourra voir la page [[technique:adminsys:tips:auth_ldap|authentification LDAP sur les machines]] ou [[technique:adminserv:wiki#changement_de_methode_d_authentification|authentification sur le Wiki avec LDAP]] pour un exemple. Cette page donne donc la structure qu'on a choisie pour les besoins de Picasoft, mais ce n'est qu'une description sémantique : un annuaire LDAP avec cette structure ne fera **rien** sans paramétrage des clients. Quand on dit : *Toute personne ayant tel groupe peut faire ceci* C'est **faux** tant que ça n'a pas été configuré comme tel. ## Général Toutes les entrées doivent avoir un attribut `cn` (Common Name) ou `ou` (Organizational Unit). Cet attribut constitue le RDN (analogie à un nom de fichier ou de répertoire). Pour les OU elles-mêmes, la valeur de `ou` est arbitraire. Pour les entrées représentant des services ou des personnes, on utilise le nom du service ou le login de la personne. ## Organizational Units Les **OU** sont des entrées qui servent essentiellement à classer leurs entrées enfants, et permettent de filtrer les recherches. On peut les voir comme des **dossiers**. On utilise trois OU : * `People`, pour stocker les comptes d'utilisateurs des machines ou des services * `Groups`, pour stocker les groupes d'utilisateurs * `Services` pour stocker les comptes des services eux-mêmes ## Groups Les entrées stockées dans l'OU `Groups` représentent des groupes sur Linux. Chaque utilisateur de l'OU `People` est associé à au moins un groupe, qui sera utilisé pour donner des permissions spécifiques sur les machines ou les services. Tous les groupes ont pour classe `posixGroup`, ce qui permet d'utiliser l'attribut `gidNumber`. Ce dernier est arbitraire : * `tech` (`500`) : ce groupe sera mappé sur le groupe `docker` des machines. Il permet donc d'administrer tous les services, mais ne donne pas de droit d'administrateurs sur les machines. * `admin` (`501`) : ce groupe sera mappé sur le groupe `sudo` des machines. Tout compte de `People` ayant un GID de `501` sera donc `sudoer` sur les machines auxquelles il a accès. * `member` (`502`) : membre de l'association. Accès basique aux machines (pas de possibilité d'utiliser Docker, par exemple). Permet de se connecter aux services réservés aux membres (Cloud, édition du Wiki...). `admin` est aussi utilisé pour les services avec authentification LDAP pour distribuer les droits d'administration. Notez que les groupes `tech`, `admin` et `member` sont prévus pour être mutuellement exclusifs : on est l'un des trois. ## People Les entrées stockées dans l'OU `People` permettent de créer des comptes d'utilisateur. C'est avec ces comptes que les personnes pourront se connecter sur les machines ou sur les services. Détaillons les classes utilisées par toutes les entrées de `People` : ### hostObject Permet d'utiliser l'attribut `host`. Cet attribut définit les accès aux machines. Il peut valoir `pica01`, `pica01-test`, `pica02`, `monitoring`, ou `*`. Il peut être dupliqué autant de fois que nécessaire, par exemple pour indiquer qu'un utilisateur a accès à `pica01` et `pica02`. ### inetOrgPerson Permet d'utiliser les attributs `mail`, `givenName` et `sn`, qui indiquent respectivement l'adresse mail, le prénom et le nom de l'utilisateur. `inetOrgPerson` propose énormément d'autres attributs qui permettent de stocker des informations génériques sur une personne. On pourra en ajouter si on en a besoin. ### ldapPublicKey Permet d'utiliser l'attribut `sshPublicKey`, qui indique la ou les clés publiques autorisées à se connecter avec ce compte. Laisser cet attribut vide interdira l'accès aux machines, mais permet l'accès aux services via le mot de passe. ### posixAccount Permet d'utiliser les attributs : * `loginShell` : Chemin du shell lors de la connexion * `homeDirectory` : Chemin du `$HOME` de l'utilisateur (créé lors de la première connexion) * `uid` : Nom d'utilisateur. En général, on choisit le même que `cn`. * `uidNumber` : UID sur la machine, nombre unique. Par convention, il commence par `2000`. * `gidNumber` GID sur la machine, c'est-à-dire le numéro du groupe primaire de l'utilisateur. Cette valeur doit correspondre aux valeurs utilisées dans les entrées de l'OU `Groups`. * `userPassword` : Mot de passe du compte. ### shadowAccount Permet d'utiliser l'attribut `shadowExpire`, qui définit une date d'expiration pour le compte, au-delà de laquelle il ne pourra plus se connecter. La date est formatée au nombre de jours écoulées depuis le 1er janvier 1970 (voir [Days Since 1970-01-01](https://www.epochconverter.com/seconds-days-since-y0) pour le calculer). Si `shadowExpire` vaut `-1`, l'utilisateur peut se connecter éternellement. ### authorizedServiceObject Permet d'utiliser l'attribut `authorizedService`, qui indique le ou les services réservés auxquels l'utilisateur peut accéder. Cet attribut est peu utilisé en pratique, mais un service peut filtrer les utilisateurs qui peuvent l'utiliser (ce serait le cas pour le mail, par exemple). ## Services Les entrées sous l'OU `Services` permettent de créer des comptes pour les services de Picasoft (e.g. Mattermost, Wekan, Wiki...) Elles sont de deux types : #### Pour interroger le LDAP Il s'agit d'entrées permettant simplement d'effectuer des requêtes sur le serveur LDAP. Par exemple, le Wiki a besoin de savoir si un utilisateur est autorisé à se connecter. Les classes de ce genre d'entrées sont `simpleSecurityObject`, pour pouvoir indiquer un mot de passe (`userPassword`), et `organizationRole`, pour pouvoir indiquer un `cn`. #### Pour avoir un compte (permissions, mail) Un service qui ne tourne pas en tant que `root`, comme Mattermost, doit bien avoir un compte POSIX disponible pour créer des fichiers. C'est fait dans le LDAP, pour éviter de le faire sur chaque machine susceptible de faire tourner Mattermost. On utilise les classes `organizationRole` et `posixAccount`, ce qui nous permet de spécifier l'UID et le GID. Le GID sera toujours celui du groupe `membre` (`502`), qui ne donne aucun accès particulier sur les machines. Aussi, certains services, comme le mail, imposent que chaque adresse mail (e.g. `mattermost@picasoft.net`) soit associé à un compte POSIX.