Classe pour PYTHON qui peut être utilisée sans connaître LDAP

introduction

J'ai résumé comment utiliser LDAP avec python en trois parties. Lors d'un développement avec plusieurs personnes, tout le monde doit comprendre la bibliothèque ldap3 et LDAP, mais cela prend du temps et des efforts. J'ai donc créé une classe pour quiconque sait seulement que LDAP est une donnée arborescente.

environnement

mérite

--Peut être utilisé sans connaître LDAP

Exemple utilisant cette classe

Tout d'abord, je décrirai comment utiliser LDAP lors de l'utilisation de cette classe. Lors de son utilisation, il sera plus facile de comprendre si vous modifiez le nom de la classe.Par conséquent, en modifiant la classe Domaine en Adresse, Organisation en Propriétaire et Commun en Animal de compagnie dans l'explication ci-dessous, vous pouvez modifier la hiérarchie Adresse-> Propriétaire-> Animal. Vous pouvez être conscient qu'il y en a.

main.py



from ldap_obj.Address import Address

#Ajouter un emplacement
address = Address('localhost', 'LdapPass', 'admin', 'sample-ldap')
address.set_item('tokyo')
address.save()

#Ajouter des personnes
owner = address.create_owner()
owner.set_item('sato')
owner.save()

#Animal de compagnie(Marbre)Ajouter
pet_tama = owner.create_pet()
pet_tama.set_item('tama')
pet_tama.save({'sn': 'sato', 'st': 'tama', 'title': 'cat'})

#Animal de compagnie(Pochi)Ajouter
pet_pocho = owner.create_pet()
pet_pocho.set_item('pochi')
pet_pocho.save({'sn': 'sato', 'st': 'pochi', 'title': 'dog'})

#Obtenez la valeur de cn à partir de la couche de domaine en utilisant le titre comme condition de recherche
address.set_filter('title')
print(address.get_common())

print('***********************')
#Générer une adresse
address_get = Address('localhost', 'LdapPass', 'admin', 'sample-ldap')
address_get.set_item('tokyo')
# Address ->Génération de propriétaires
owner_get = address_get.create_owner()
owner_get.set_item('sato')
# Address -> Owner ->Génération d'animaux de compagnie
pet_get = owner_get.create_pet()
pet_get.set_item('tama')
print(pet_get.get_common())

Classe pour LDAP

La classe LDAP crée une classe pour chaque hiérarchie.

Structure du répertoire

\--
  |--ldap_obj\
  |    |--BaseClass.py (Classe de critères)
  |    |--CommonClass.py (classe de cn)
  |    |--DomainClass.py (classe dc)
  |    |--OrganizationClass.py (ou classe)
  |
  |--main.py

Classe de critères

La classe de base est essentiellement un wrapper pour ldap3. Je ne fais rien de particulièrement compliqué. L'entrepreneur génère la classe requise pour la connexion, et get_xxx () passe la classe d'objet à _read_ldap () pour obtenir les informations de LDAP. Cette fonction augmentera à mesure que le nombre de classes d'objets augmente.

BaseClass.py



from ldap3 import Server, Connection, ObjectDef, Reader

class BaseClass(object):

    def __init__(self, host, passwd, user, top_domain, dn=None):
        self.passwd = passwd
        self.user = user
        self.host = host
        self.top_domain = top_domain
        self.filter = None

        if (dn):
            self.dn = dn
        else:
            self.dn = 'dc=' + top_domain
        
        self.server = Server(self.host)
        self.conn = Connection(self.host, 'cn={},dc={}'.format(user, top_domain),  password=passwd)

    def set_filter(self, filter):
        self.filter = filter
    
    def get_domain(self):
        return self._read_ldap('domain', self.filter)

    def get_organizational(self):
        return self._read_ldap('organizationalUnit', self.filter)

    def get_common(self):
        return self._read_ldap('inetOrgPerson', self.filter)

    def get_domain_dict(self):
        return self._read_ldap_dict('domain', self.filter)

    def get_organizational_dict(self):
        return self._read_ldap_dict('organizationalUnit', self.filter)

    def get_common_dict(self):
        return self._read_ldap_dict('inetOrgPerson', self.filter)

    def _read_ldap(self, object_type, search_attr = None):
        data_list = []
        self.conn.bind()
        obj_dn = ObjectDef(object_type, self.conn)
        data_reader = Reader(self.conn, obj_dn, self.dn)
        data_reader.search(search_attr)
        for data in data_reader:
            data_list.append(data)

        data_reader.reset()
        self.conn.unbind()
        return data_list

    def _read_ldap_dict(self, object_type, search_attr = None):
        data_list = []
        self.conn.bind()
        obj_dn = ObjectDef(object_type, self.conn)
        data_reader = Reader(self.conn, obj_dn, self.dn)
        data_reader.search(search_attr)
        for data in data_reader:
            data_list.append(data.entry_attributes_as_dict)

        data_reader.reset()
        self.conn.unbind()
        return data_list

Classe d'extension

Créez une classe qui hérite de la classe standard ci-dessus pour chaque hiérarchie.

Classe de domaine

Puisque la valeur de dc est requise, la valeur de dc est ajoutée à la chaîne de caractères de dn avec set_item () ''. Utilisez ce self.dn pour obtenir des informations avec la classe de base `get_xxx ()` , ou ajoutez-la avec`` save () `` . create_organization () '' `` crée et retourne une classe pour ou. Dans cet exemple, nous voulons dc = xxx, ou = yyy, il n'y a donc qu'une fonction de génération pour ou, mais si vous voulez dc = xxx, dc = yyy, vous pouvez créer une fonction de génération pour dc de la même manière.

DomainClass.py



from ldap_obj.BaseClass import BaseClass
from ldap_obj.OrganizationClass import OrganizationClass

class DomainClass(BaseClass):
         
    def set_item(self, item):
        self.dn = 'dc=' + item + ',' + self.dn

    def create_organization(self):
        return OrganizationClass(self.host, self.passwd, self.user, self.top_domain, self.dn)

    def save(self):
        self.conn.bind()
        result = self.conn.add(self.dn, 'domain')
        self.conn.unbind()
        return result

Classe d'organisation

Puisque la classe Organization générée à partir de la classe Domain contient le chemin d'accès à cn dans self.dn, la valeur de ou est ajoutée avec set_item () ''. Utilisez ce self.dn pour obtenir des informations avec la classe de base get_xxx () `, ou ajoutez-la avec save () `. create_common () '' crée et retourne une classe pour cn. Dans cet exemple, je veux dc = xxx, ou = yyy, cn = zzzz, donc il n'y a qu'une fonction de génération pour cn, mais si vous voulez avoir une autre configuration, créez une fonction de génération pour cela.

OrganizationClass.py



from ldap_obj.BaseClass import BaseClass
from ldap_obj.CommonClass import CommonClass

class OrganizationClass(BaseClass):

    def set_item(self, item):
        self.dn = 'ou=' + item + ',' + self.dn

    def create_common(self):
        return CommonClass(self.host, self.passwd, self.user, self.top_domain, self.dn)

    def save(self):
        self.conn.bind()
        result = self.conn.add(self.dn, 'organizationalUnit')
        self.conn.unbind()
        return result

Classe commune

Puisque la classe Common générée à partir de la classe Organization contient le chemin vers ou dans self.dn, la valeur de cn est ajoutée avec set_item () ''. Utilisez ce self.dn pour obtenir des informations avec la classe de base get_xxx () `, ou ajoutez-la avec save () `` `. Comme cet exemple est le dernier de ce cn, il n'y a pas de fonction de génération, mais si la hiérarchie est plus profonde, créez une fonction de génération pour elle.

CommonClass.py



from ldap_obj.BaseClass import BaseClass

class CommonClass(BaseClass):

    def set_item(self, item):
        self.dn = 'cn=' + item + ',' + self.dn

    def save(self, attr_dict):
        self.conn.bind()
        result = self.conn.add(self.dn, 'inetOrgPerson', attr_dict)
        self.conn.unbind()
        return result

Fonction principale de l'appelant

Pour utiliser ces classes, générez d'abord une DomainClass puis entrez la valeur de dc, puis utilisez la DomainClass générée create_organization () '' pour créer une classe Organization et la valeur de ou. Mettez dedans. Pour créer du commun, utilisez la classe Organisation générée create_common () '' et entrez la valeur de cn. Utilisez la fonction get et des fonctions supplémentaires dans chaque classe de génération pour faire fonctionner LDAP.

main.py



from ldap_obj.DomainClass import DomainClass

domain = DomainClass('localhost', 'LdapPass', 'admin', 'sample-ldap')
domain.set_item('sample-component')
domain_item_list = domain.get_domain()
for domain_item in domain_item_list:
    print(domain_item)

print("=====================")

domain.set_filter('st')
domain_item_list = domain.get_common()
for domain_item in domain_item_list:
    print(domain_item)

print("=====================")

organization = domain.create_organization()
organization.set_item('sample-unit')
organization_list = organization.get_organizational()
for organization_item in organization_list:
    print(organization_item)

print("=====================")

common = organization.create_common()
common.set_item('sample-name')
common_list = common.get_common()
for common_item in common_list:
    print(common_item)

print("***********************************")

new_domain = DomainClass('localhost', 'LdapPass', 'admin', 'sample-ldap')
new_domain.set_item('new-component')
print(new_domain.save())
print("=====================")

new_organization = new_domain.create_organization()
new_organization.set_item('new-organization')
print(new_organization.save())
print("=====================")

new_common = new_organization.create_common()
new_common.set_item('new-common')
print(new_common.save({'st':'new-st', 'sn': 'new-sn'}))
print("=====================")

new_common_list = new_common.get_common()
for common_item in new_common_list:
    print(common_item)

en conclusion

J'ai essayé de créer une classe qui peut être exploitée en éliminant autant que possible les éléments LDAP. Si vous connaissez la bibliothèque de ldap3, l'opération via la classe semble gênante, mais lorsque vous regardez réellement la source, il devient plus facile de comprendre ce que vous faites en un coup d'œil. Cette fois j'ai ajouté les fonctions get et add, mais je pense que supprimer, déplacer et mettre à jour devrait ajouter une fonction qui utilise ldap3 à la classe standard. S'il est facile à comprendre jusqu'à présent, je pense qu'il n'y aura aucune hésitation à l'utiliser comme candidat au stockage de données.

Recommended Posts

Classe pour PYTHON qui peut être utilisée sans connaître LDAP
J'ai créé un modèle de projet Python générique
Peut être utilisé avec AtCoder! Une collection de techniques pour dessiner du code court en Python!
[Python] Un programme pour trouver le nombre de pommes et d'oranges qui peuvent être récoltées
Enquête sur l'alimentation CC contrôlable par Python
Création d'une bibliothèque pour python capable de gérer facilement la division morphologique
À partir d'un livre que les programmeurs peuvent apprendre ... (Python): examen des tableaux
J'ai fait un shuffle qui peut être réinitialisé (inversé) avec Python
[python] J'ai créé une classe qui peut écrire rapidement une arborescence de fichiers
Comprendre les probabilités et les statistiques qui peuvent être utilisées pour la gestion des progrès avec un programme python
[Python] Un programme qui trouve le nombre maximum de jouets pouvant être achetés avec votre argent
J'ai écrit un tri-arbre qui peut être utilisé pour l'implémentation de dictionnaire à grande vitesse en langage D et Python
[Python] Un programme qui trouve une paire qui peut être divisée par une valeur spécifiée
[Python] Un programme qui calcule le nombre de chaussettes jumelées
Un mémo lors de la création d'un environnement qui peut être débogué avec Lambda @ Edge pour le moment
Optimisation mathématique pour un travail gratuit avec Python + PuLP
Résumé du livre électronique Python utile pour l'analyse de données gratuite
Un script python pour Mac qui zippe sans caractères déformés sous Windows
Article qui peut être une ressource humaine qui comprend et maîtrise le mécanisme de l'API (avec du code Python)
Notes pour créer des figures pouvant être publiées dans des revues avec matplotlib
J'ai essayé de créer une classe qui peut facilement sérialiser Json en Python
Vous pouvez appeler la méthode de la classe directement dans Python3 sans ajouter @staticmethod
À partir d'un livre que les programmeurs peuvent apprendre (Python): Déclaration de classe (public / privé, etc.)
Je souhaite créer une file d'attente prioritaire pouvant être mise à jour avec Python (2.7)
Notes personnelles des opérations liées aux pandas qui peuvent être utilisées dans la pratique
Comment installer la bibliothèque Python qui peut être utilisée par les sociétés pharmaceutiques
Une collection de ressources qui peuvent être utiles pour créer et développer des fichiers dotfiles
Fonctions pouvant être utilisées dans l'instruction for
[Python / Tkinter] Une classe qui crée un cadre défilable
Python: préparez un sérialiseur pour l'instance de classe:
Python: créer une classe qui prend en charge l'affectation décompressée
Présentation et fonctionnalités utiles de scikit-learn qui peuvent également être utilisées pour l'apprentissage en profondeur
Résumé des méthodes d'analyse de données statistiques utilisant Python qui peuvent être utilisées en entreprise
Un script python qui obtient le nombre de travaux pour une condition spécifiée sur Indeed.com
Visualisation des informations géographiques de R et Python qui peuvent être exprimées par Power BI
[Python] Introduction au scraping WEB | Résumé des méthodes pouvant être utilisées avec webdriver
Comment créer une propriété de relations qui peuvent être prefetch_related par des conditions spécifiques
Un mécanisme pour appeler des méthodes Ruby à partir de Python qui peut être fait en 200 lignes
[Python] Un programme qui compte le nombre de vallées
J'ai créé une VM qui exécute OpenCV pour Python
Implémentation python de la classe de régression linéaire bayésienne
Notes sur les connaissances Python utilisables avec AtCoder
Python qui fusionne beaucoup d'excellence en un seul Excel
D'un livre que les programmeurs peuvent apprendre ... (Python): Pointer
Ne pas être conscient du contenu des données en python
Python: obtenir une liste de méthodes pour un objet
[Python] Un programme qui compare les positions des kangourous.
Comment démarrer un serveur WEB simple qui peut exécuter des cgi de php et python
Comment configurer un serveur SMTP simple qui peut être testé localement en Python
Étant donné que ImageDataGenerator ne peut plus être utilisé, une histoire sur la création d'une classe d'extension de données pour tensorflow> = 2.0
Récapitulatif du format des formats qui peuvent être sérialisés avec gensim
Votre dll est-elle une dll qui peut tirer parti du multi-core?
Connaissance de base du DNS qui ne peut pas être entendue maintenant
Pourquoi les commandes Linux peuvent-elles être exécutées sans écrire un PATH?
À partir d'un livre que les programmeurs peuvent apprendre ... (Python): À propos du tri
Les zéros NumPy peuvent être définis même avec une taille de 0
traitement python3 qui semble utilisable dans paiza