Exemple #1
0
class Directory(object):
    """XXX: this could be without base_dn, not supporting iteration
    """
    def __init__(self, uri, base_dn, bind_dn, pw):
        self.base_dn = base_dn
        self._ldap = LDAPObject(uri)
        self._ldap.bind_s(bind_dn, pw)

    def __contains__(self, dn):
        try:
            return dn == self._ldap.search_s(dn, SCOPE_BASE,
                                             attrlist=[''])[0][0]
        except ldap.NO_SUCH_OBJECT:
            return False

    def __getitem__(self, dn):
        try:
            entry = self._ldap.search_s(dn, SCOPE_BASE)[0]
        except ldap.NO_SUCH_OBJECT:
            raise KeyError(dn)
        node = Node(name=dn, attrs=entry[1], ldap=self._ldap)
        return node

    def __setitem__(self, dn, node):
        addlist = node.attrs.items()
        try:
            self._ldap.add_s(dn, addlist)
        except ldap.ALREADY_EXISTS:
            del self[dn]
            self._ldap.add_s(dn, addlist)

    def __delitem__(self, dn):
        try:
            self._ldap.delete_s(dn)
        except ldap.NO_SUCH_OBJECT:
            raise KeyError(dn)

    def __iter__(self):
        return (x[0][0] for x in
                self._search(self.base_dn, SCOPE_SUBTREE)
                if x[0][0] != self.base_dn)

    def _search(self, base, scope, filterstr='(objectClass=*)', attrlist=None,
                timeout=-1):
        """asynchronous ldap search returning a generator
        """
        msgid = self._ldap.search(base, scope,
                                  filterstr=filterstr, attrlist=attrlist)
        rtype = ldap.RES_SEARCH_ENTRY
        while rtype is ldap.RES_SEARCH_ENTRY:
            # Fetch results single file, the final result (usually)
            # has an empty field. <sigh>
            (rtype, data) = self._ldap.result(msgid=msgid, all=0,
                                              timeout=timeout)
            if rtype is ldap.RES_SEARCH_ENTRY or data:
                yield data

    def items(self):
        return ItemsView(dictionary=self)

    def keys(self):
        return KeysView(dictionary=self)

    def values(self):
        return ValuesView(dictionary=self)

    def __len__(self):
        return sum(1 for node in iter(self))

    def clear(self):
        for dn in self.keys():
            del self[dn]

    def copy(self):
        return copy.copy(self)

    def get(self, dn, default=None):
        try:
            return self[dn]
        except KeyError:
            return default

    def pop(self, dn, default=None):
        try:
            node = self[dn]
            del self[dn]
        except KeyError:
            if default is None:
                raise KeyError(dn)
            return default
        return node

    def popitem(self):
        if not self:
          raise KeyError
        dn = next(iter(self))
        node = self[dn]
        del self[dn]
        return (dn, node)

    def setdefault(self, dn, default=None):
        try:
            return self[dn]
        except KeyError:
            self[default.name] = default
            return default

    def update(self, other):
        try:
            items = other.items()
        except AttributeError:
            items = other
        for dn, node in items:
            self[dn] = node
        return None

    iterkeys = __iter__

    def itervalues(self):
        return (Node(name=x[0][0], attrs=x[0][1], ldap=self._ldap) for x in
                self._search(self.base_dn,
                                  ldap.SCOPE_SUBTREE, attrlist=[''])
                if x[0][0] != self.base_dn)

    def iteritems(self):
        return ((node.name, node) for node in ValuesView(self))