LDAP Bind: Verbindung mit dem Verzeichnis herstellen
Um auf einen Verzeichnis-Dienst zugreifen zu können, müssen wir zuerst eine technische Verbindung zu einem Objekt im Verzeichnis herstellen. Es kann sich hierbei um einen Verzeichnis-Container (z.B. eine Organisational Unit) oder ein einzelnes Objekt handeln.
Da der technische Zugriff hierbei mittels des LDAP-Protokolls durchgeführt wird, verwenden wir auch die entsprechende LDAP-Sprechweise: Das Herstellen einer Verbindung und die Anmeldung mit entsprechenden Anmeldeinformationen nennt man BindOperation (dies hat nichts mit dem gleichnamigen DNS-Server zu tun).
Viele Aspekte des Bindings werden im MSDN beschrieben: MSDN-Dokumentation zu ADSI und Bind.
Falls nicht anders erwähnt, wird in diesem Abschnitt stets ein Bind auf Active Directory Objekte durchgeführt. Die ADSI-Schnittstelle erlaubt sehr wohl auch Bind-Vorgänge an andere Verzeichnisdienste. Beispiele dafür finden Sie weiter unten auf dieser Seite.
Bind-Varianten:
Bind mit der User-ID, mit der auch das Skript ausgeführt wird
Die einfachste Form der Verbindung. Man "schnappt" sich das Objekt für den Zugriff mit einem einfachen GetObject-Befehl. Hierbei wird zur Authentifizierung automatisch die ID des Users verwendet, der das Skript ausführt. Diese Methode eignet sich also nur für Zugriffe in den eigenen Forest, falls man über ausreichende Rechte verfügt. Wichtig ist auch die Schreibweise des LDAP-Pfadnamens (insbesondere wenn dort Kommata oder andere besondere Zeichen vorkommen!).
Danach kann über die Variable obj das Objekt "Philipp" aus der OU "Benutzer" der Domäne "cerrotorre.de" zugegriffen werden. Ein Zugriff ist jedoch auch auf alle Objekte eines Containers möglich:
Serverless Binding:
Bedenken Sie, dass in Active Directory Umgebungen bei der Angabe des LDAP-Pfadnamens der
Servername auch weggelassen werden kann - dann sucht sich der Rechner,
auf dem das Skript läuft, automatisch (per DNS) einen Domänen-Controller
aus der Domäne des Users, der das Skript ausführt. Insbesondere
kann man einen verkürzten LDAP-Pfadnamen verwenden, wenn das Skript
direkt auf einem Domänen-Controller der betreffenden Domäne ausgeführt
wird:
Serverless Binding sollte nicht eingesetzt werden, wenn Sie für andere Verzeichnisdienste wie z.B. im Lotus Notes LDAP oder eDirectory entwicklen. Hier können Sie Serverless Binding nicht verwenden.
Bind unter Angabe von speziellen Anmeldedaten
Die normale Methode des Verzeichnis-Binds funktioniert immer dann, wenn ich als angemeldeter User auf Objekte aus meiner eigenen Domäne bzw. aus meinem eigenen Active Directory Forest zugreifen will. Oft ist es jedoch notwendig, auf ein Verzeichnis-System zuzugreifen, bei dem man aktuell nicht als User authentifiziert ist. Hier gibt es die Bind-Variante mit dem Befehl OpenDSObject, der die Übergabe von Username und Passwort erlaubt und so eine Anmeldung z.B. auch an fremde Forests ermöglicht.
In unserem Beispiel wird also das OU-Objekt in der Domäne "cerrotorre.de zugegriffen, wobei zu diesem Zweck am Server controller.cerrotorre.de eine Anmeldung mit Username "administrator" und Passwort "P@ssw0rd" stattfindet. Der letze Parameter (1) führt als Anmelde-Flag dazu, dass eine gesicherte Kerberos-Anmeldung stattfindet.
ADSI-Referenz
im MSDN: OpenDSObject()
Der Benutzername kann bei einer AD-Anmeldung in folgender Form angegeben
werden:
Anmedename ohne Zusätze | z.B. "administrator", hierzu
muss das Anmelde-Flag jedoch auf 1 gesetzt werden (gesicherte Anmeldung) |
NetBIOS-Anmeldename | z.B. "DOMAIN\administrator" |
User Principal Name | z.B. "administrator@domain.com" |
Distinguished Name | z.B. "cn=administrator,cn=users,dc=domain,dc=com", hierzu muss das Anmelde-Flag jedoch auf 0 (Klartext-Anmeldung) stehen. |
Das Anmelde-Flag bestimmt die Art der Anmeldung. Prinzipiell interessant sind die beiden Werte 0 (für unverschlüsselte Anmeldung im Klartext) und 1 (für gesicherte Anmeldung über Kerberos oder NTLM). Eine gesicherte Anmeldung ist der Klartextanmeldung natürlich vorzuziehen. Allerdings kann es auch Situationen geben, wo eine ungesicherte Klartext-Anmeldung benötigt wird. Insbesondere bei der Bind-Anmeldung an anderen Verzeichnisdiensten wie z.B. Novells eDirectory oder OpenLDAP-Systemen muss das Anmelde-Flag auf 0 gesetzt werden. Um ein Ausspähen des Kennwortes auf dem Netz zu verhindern, bietet sich hier die Benutzung von LDAP-SSL an - dann wird der gesamte LDAP-Protokollverkehr verschlüsselt.
Microsoft-Erläuterungen zum Anmelde-Flag im MSDN
Man kann in Active Directory Umgebungen im LDAP-Pfadnamen den Servernamen weglassen, dann wird automatisch an einen erreichbaren Domänen-Controller der eigenen Domäne gefunden. Ebenso kann man als Username und Passwort jeweils den NULL-String ("") übergeben, dann werden automatisch die Anmeldedaten des eigenen Benutzers verwendet. Diese Möglichkeiten dürften jedoch nutzlos sein, da man sich mit dieser Bind-Variante wahrscheinlich an einem anderen Forest-DC anmelden will - also muss man den Server und die Anmeldedaten passend angeben.
Bind an den globalen Katalog
Wenn Sie Sich mit Hilfe von ADSI mit einen Domänen-Controller verbinden,
dann kann dieser lediglich Daten aus der Schema Partition,
der Configuration Partition und der eigenen Domäne
liefern. Wollen Sie jedoch Objekte des gesamten Forests von einem einzigen
Domänen-Controller abfragen, so müssen Sie sich mit einem Globalen
Katalog (GC) verbinden. Dieser stellt auch Objekte aus anderen
Domänen zur Verfügung, und zwar über LDAP über den
speziellen TCP-Port 3268.
Allerdings können diese Objekte nur gelesen werden und verfügen
nur über einen Ausschnitt der wichtigsten Attribute!
Als technische Variante kann man für den Bind am globalen Katalog
den LDAP-Pfadnamen so verändern, dass die
TCP-Port-Nummer 3268 verwendet wird. Dies funktioniert sowohl über
die Funktion GetObject als auch mit OpenDSObject.
Voraussetzung ist hierbei natürlich, dass der angesprochene Server
"server.cerrotorre.de" auch als globaler Katalog konfiguriert wurde.
Eine einfachere Variante, die eine Sonderform des Pfadnamens ausnutzt,
wobei der Ausdruck "LDAP" durch "GC" ersetzt wird.
Dann braucht auch die spezielle Port-Nummer 3268 nicht angegeben zu werden:
Auch hierbei können Sie in Active Directory Umgebungen ein Serverless Binding durchführen, dann wird ein globaler Katalog automatisch über DNS gesucht:
Bind, wenn der eigene Domänenname / Forest nicht bekannt ist
Oft will man Skripte entwickeln, die in verschiedenen Active Directory Umgebungen laufen.
Stellen Sie sich z.B. ein Skript vor, dass in der eigenen Domäne irgendwelche
Infos zu diversen Objekten ausgibt oder spezielle Änderungen vornimmt.
Damit das Skript in beliebigen Domänen läuft, könnte man
natürlich den Domänen-Namen als Parameter übergeben lassen.
Aber noch eleganter ist es, den Domänen-Namen zu ermiteln, indem man
mit einem Serverless Binding das Active Directory selbst danach fragt.
Die entsprechenden Informationen stehen in einem speziellen Verzeichnis-Eintrag,
der auf jedem Domänen-Controller zur Verfügung steht: dem rootDSE-Eintrag
(Root Directory Service Entry).
Wir können hier aus der Eigenschaft "defaultNamingContext"
den Distinguished Name der eigenen Domäne entnehmen und daraus gleich
einen LDAP-Pfadnamen bauen, mit dem auf die
gewünschten Domänen-Objekte zugegriffen werden kann.
Dieses Script zählt alle Objekte direkt im Haupt-Namenskontext einer Active Directory Domäne auf - dies ist der Container, in dem alle "normalen" User- und Gruppenobjekte gespeichert werden. Man kann übrigens auch (mit den entsprechenden Rechten) auf den Configuration Container des Forests zugreifen, ohne die genaue Bezeichnung zu kennen. Der betreffende DN steht nämlich als "configurationNamingContext"-Eigenschaft im rootDSE-Eintrag.
Bind als Anonymous
LDAP bietet generell die Möglichkeit einer Anmeldung ohne Benutzerdaten. Es handelt sich dann um einen sogenannten Anonymous Bind Vorgang. Es hängt allerdings von der Einstellung des jeweiligen Verzeichnisdienstes ab, ob diese anonyme Anmeldung erlaubt ist. Wenn ja, hat der anonyme LDAP-Benutzer meist nur eingeschränkte Berechtigungen im betreffenden Verzeichnis.
Wenn Sie sich als anonymer Benutzer ohne User-Name und Passwort an einem Active Directory anmelden wollen, so muss man hier zwischen alten Windows 2000-Forests und Forests unterscheiden, die mit Versionen ab Windows 2003 betrieben werden.
AD unter Windows 2000: Hier wird die anonyme Anmeldung
standardmäßig zugelassen. |
|
AD unter Windows 2003 (und höher): Hier wird der anonyme Zugriff zunächst prinzipiell auf den rootDSE-Eintrag (Root Directory Service Entry) beschränkt. Man kann also z.B. eine Liste der Naming Contextes oder die Active Directory Version des Forests auslesen. Wenn man jedoch anonym auf die Normalen Objekte und Attribute des Forests zugreifen möchte, so muss dies erst durch einen globalen Schalter erlaubt werden. Es handelt sich dabei um das AD-Attribut dsHeuristic. Wie man dieses Attribut setzt, erfahren Sie im HowTo-Artikel "Anonyme LDAP-Anmeldungen in einer Umgebung unter Windows 2003 (und höher) zulassen". |
Vergessen Sie nicht: Auf welche Objekte und Attribute man dann zugreifen darf, entscheidet sich auch daran, welche Berechtigungen für die Einträge ANONYMOUS LOGON und Everyone in den betreffenden ACLs vorhanden sind. Im Originalzustand haben diese beiden Einträge keinerlei Berechtigung auf Objekte der Domäne zuzugreifen - selbst wenn durch dsHeuristics dies anonyme Anmeldung prinzipiell erlaubt wurde.
Außerdem ist nun beim Bind-Vorgang einiges zu beachten. Ein anonymer Benutzer kann nämlich nicht so ohne weiteres den Inhalt von Container-Objekten sehen, man muss direkt per kompletten LDAP-Pfad auf einzelne Objekte wie User, Gruppen oder Kontakte zugreifen. Dabei verwendet man die Anmeldung mit der Funktion OpenDSObject, jedoch ohne Username und Passwort:
Wenn sie auf viele Objekte zugreifen wollen bzw. wenn Sie die konkreten LDAP-Pfade nicht kennen, dann bleibt immer noch die Möglichkeit einer Verzeichnis-Suche über die ADO-Schnittstelle. Die Durchführung einer ADO-Suche wird im SelfADSI-Tutorial im Abschnit "Objekte im Verzeichnis suchen" ausführlich erklärt.
Für eine anonyme ADO-Abfrage gegen ein Active Directory müssen wir allerdings einige Modifikationen vornehmen. Zum einen wird der Base-String der Verzeichnissuche weggelassen - als anonymer Benutzer kann man schließlich keine Verzeichnis-Container "sehen".
Zum anderen muß man bei der Suche den Global Catalog Provider verwenden, denn nur dieser erlaubt eine Suche ohne definierten Base-String. Die Suche beginnt direkt bei dem folgenden LDAP-Pfad:
<GC://Server>
Hier ein Beispiel, in dem alle Benutzer-Objekte angezeigt werden. Für eine Zugriff auf andere Objekte verändern Sie einfach den LDAP-Filter:
Beachten Sie hierbei bitte, dass eine ADO-Suchanfrage an den Global Catalog entsprechende LDAP-Pfadnamen aus dem gesamten Forest zurückgibt (wir hatten schließlich nach der Eigenschaft "ADSPath" gefragt...). Die zurückgegebenen LDAP-Pfadnamen des Global Catalogs werden mit der Protokoll-Kennung "GC://" aufgeführt, wie Sie an der Ausgabe des obigen Skriptbeispiels sehen können:
Bei einem nachfolgenden Connect an diese Pfadnamen können Sie weder alle Attribute lesen noch Eigenschaften schreibend verändern - sie greifen schließlich auf den Global Catalog zu! Informieren Sie sich über den Umgang mit Suchergebnissen des Global Catalogs am Besten im Abschnitt "Der Global Catalog" hier im SelfADSI Tutorial.
Bind an Novell eDirectory / NDS Server
Wenn Sie sich mit einem Exchange 5.5-Server verbinden wollen, um dort
auf Mailbox-Informationen oder die Konfiguration der Mail-Organisation
zuzugreifen, müssen Sie einige Dinge beachten.
Zuerst einmal müssen Sie sich bewusst sein, dass in Novell eDirectory-Verzeichnissen
der LDAP-Pfadnamen eine andere Form hat als
man es von Active Directory gewohnt ist: Anstatt einer Domäne (z.B.
...,dc=cerrotorre,dc=de) wird die oberste Hierarchie in einem solchen Verzeichnis
von einer Organisation (...,o=...) oder Country-Objekt (...,c=...) gebildet.
cn=PFoeckel,ou=Karlsruhe,o=CerroTorre
cn=BierSan,ou=Students,ou=Sydney,c=au
Außerdem muss man beim Bind-Vorgang stets mit der Funktion OpenDSObject arbeiten
und dabei den betreffenden Novell-Server direkt mit angeben (und gegebenenfalls
auch die LDAP-Portnummer, mit der der Server konfiguriert ist). Als Usernamen
verwendet man den kompletten LDAP-Pfadnamen des
anzumeldenen Users, als Anmelde-Flag muss
stets 0 verwendet werden:
Die Anmeldung mit unverschlüsseltem Passwort ist natürlich ziemlich unsicher, aber man kann bei passender Ausstattung des Servers mit einem SSL-Zertifikat ja auch LDAP-SSL auf TCP-Port 636 verwenden, dann wird die gesamte LDAP-Kommunikation und damit auch Username und Passwort in einem SSL-Tunnel verschlüsselt.
Wenn man sich anonym am eDirectory anmelden will, dann übergibt man statt Username und Passwort einfach einen leeren String. Novell-Server lassen die anonyme Anmeldung prinzipiell zu, allerdings hat man dann natürlich nur dort Zugriff, wo der Eintrag [Public] als Trustee vorhanden ist:
Bind an Exchange 5.5-Server
Wenn Sie sich mit einem Exchange 5.5-Server verbinden wollen, um dort
auf Mailbox-Informationen oder die Konfiguration der Mail-Organisation
zuzugreifen, müssen Sie einige Dinge beachten.
Zuerst einmal müssen Sie sich bewußt sein, dass in Exchange
5.5-Verzeichnissen der LDAP-Pfadnamen eine andere
Form hat: Bei einer Organisation mit der Bezeichnung "Firma-Mail" würde
der Empfänger-Container im Standort "Karlsruhe"
folgenden Pfadnamen besitzen:
cn=Recipients,ou=Karlsruhe,o=Firma-Mail
Außerdem muss man beim Bind-Vorgang stets mit der Funktion OpenDSObject arbeiten
und dabei den betreffenden Exchange-Server direkt mit angeben (und gegebenenfalls
auch die LDAP-Portnummer, mit der der Server konfiguriert ist). Als Usernamen
verwendet man am besten den NetBIOS-Anmeldename eines User mit entsprechenden
Rechten im Exchange-Verzeichnis, als Anmelde-Flag muss 1 verwendet werden:
Außerdem besitzt Exchange 5.5 als LDAP-Server die lästige Angewohnheit,
dass man nicht ohne weiteres an Objekte herankommt, die nicht im Adressbuch
angezeigt werden. Dies kann man umgehen, indem man in der Funktion OpenDSObject
eine besondere Form des Anmeldenamens verwendet:
cn=<Username>, dc=<Domäne>, cn=admin
Mit dieser administrativen Bind-Anmeldung kann man neben den normalen Objekten
auch versteckte oder sogar gelöschte (in der DIR-Datenbank noch vorhandene)
Objekte zugreifen.
Versteckte Objekte sind Objekte, bei denen das LDAP-Attribut Hide-From-Address-Book auf
TRUE steht.
Gelöschte Objekte sind Objekte, bei denen das LDAP-Attribut Is-Deleted auf
TRUE steht.
Ein Beispiel für einen solchen Zugriff:
Beachten Sie dabei, dass die Anmeldung mit dem Authentication Flag 0 (für Simple Auth mit Klartextkennwort) erfolgen muß.
Bind als Anonymous an Exchange 5.5-Server
Wenn Sie sich als anonymer Benutzer ohne User-Name und Passwort an einem Exchange 5.5-Server anmelden wollen, so muss dies am betreffenden Server oder in der betreffenden Exchange 5.5-Site zuerst explizit erlaubt werden:
Ab diesem Moment wird ein Client, der einen Bind-Versuch mit leerem Benutzernamen und Passwort unternimmt, als anonymer Benutzer angemeldet und hat dann Zugriff auf Verzeichnis-Informationen - allerdings nur diejenigen, die auch für den anonymen Zugriff freigegeben sind. Auf welche Attribute ein anonym angemeldeter LDAP-Client zugreifen darf, kann man in der DS Site Konfiguration des betreffenden Exchange 5.5-Standortes eingesehen und verändert werden.
Allerdings hat man nun beim Bind-Vorgang einiges zu beachten. Ein anonymer Benutzer kann nämlich keine Container-Objekte sehen, man muß direkt per kompletten LDAP-Pfad auf einzelne Objekte wie Postfächer, Custom Recipients oder Verteilerlisten zugreifen. Dabei verwendet man die Anmeldung mit der Funktion OpenDSObject, jedoch ohne Username und Passwort:
Wenn sie auf viele Objekte zugreifen wollen bzw. wenn Sie die konkreten LDAP-Pfade nicht kennen, dann bleibt immer noch die Möglichkeit einer Verzeichnis-Suche über die ADO-Schnittstelle. Die Durchführung einer ADO-Suche wird im SelfADSI-Tutorial im Abschnit "Objekte im Verzeichnis suchen" ausführlich erklärt.
Für eine anonyme ADO-Abfrage gegen einen Exchange 5.5-Server müssen wir allerdings einige Modifikationen vornehmen. Diese werden im Microsoft KnowledgeBase-Artikel Q223049 erläutert. Zum einen wird der Base-String der Verzeichnissuche weggelassen - zum anderen muss im LDAP-Pfadnamen der Global-Catalog Provider mit LDAP-Port 389 (oder dem konfigurierten LDAP-Port des betreffenden Servers) angegeben werden. Dieser Provider ist ansonsten für Exchange 5.5-Vereichniszugriffe sinnlos, da nur Active Directory Verzeichnisse eine Global Catalog Funktion haben. In unserem Falle jedoch verwenden wir diesen Trick, um anonym eine ADO-Suche durchführen zu können.
Eine dritte Änderung gegenüber einer normalen ADO-Suche im Verzeichnis ist die explizite Erzeugung eines ADODB.Command Objektes, weil man dessen Eigenschaften PageSize bei der anonymen Abfrage benötigt. Hier ein Beispiel, in dem alle Postfach-Objekte angezeigt werden. Für eine Zugriff auf andere Objekte verändern Sie einfach den LDAP-Filter: