使用NET类和 LDAP 查询 Active Directory

介绍

本文介绍如何使用。NET框架在Windows Active Directory服务管理资源。微软提供活动目录服务接口(ADSI),它可以与许多供应商,包括IIS(Internet信息服务),LDAP(轻量级目录访问协议),WinNT和Novell NetWare目录服务(NDS),
因为我的目的是展示的NET DirectoryService Classes的使用,所以我限制演示项目查询一些常用资源的计算机,用户和打印机在用户的机器所在的域,同时显示的效率,Active Directory Service 的难易程度及Active Directory可以检索对象。

我也用LDAP在本演示中,因为我想知道这个协议,因为它是一个独立于平台的协议,这将是有用的。

有不同的方式查询在C#程序中的Active Directory服务

  • 使用ADSI通过COM互操作。对于这一点,在Visual Studio C#项目“添加引用...” 然后选择“COM”选项卡上,从列表中选择活动DS类型库添加使用ActiveDs;语句到文件的开头或使用完全合格的类名来访问ADSI功能。
  • 使用Active Directory服务OLEDB提供程序ADsDSOObject 这种方法主要是在SQL Server中的链接服务器的Active Directory作为有益的补充。这门课程的范围的一篇文章中,我将讨论如何查询Active Directory使用ADS OLEDB提供程序在不同的文章。
  • 使用。NET下的System.DirectoryServices命名空间提供的类要访问这些类添加System.DirectoryServices.dll的参考文献。本文演示了这种方法。

。NET System.DirectoryServices命名空间

System.DirectoryServices命名空间提供了两个重要的类的DirectoryEntry 的DirectorySearcher工作与Active Directory。DirectoryEntry类的资源在Active Directory中,DirectorySearcher类是用来查询Active Directory。这个命名空间下的类。NET的安全性和集合类支持上面所说的主类。
的System.DirectoryServices添加到您的参考。NET选项卡中添加引用对话框中选择System.DirectoryServices.dll

LDAP格式的过滤字符串

DirectorySearcher类使用一个搜索根目录,这是一个服务器开始搜索和LDAP过滤字符串(这是类似于where子句中的SQL)来查询Active Directory资源。LDAP过滤字符串格式是类似LISP。括在括号中的条件和操作员前面2个条件。例如:(&(A)(B))的声明是等于说A和B还记得括号。应解释为另一示例(|(&(A)(B))(C))(A和B)或(C)。

OLAP条件语句是由使 ​​用Active Directory属性,如 name,objectCategory, objectClass, printerName, ListedName 等组成。例如打印机列表的查询条件是objectCategory=printQueueobjectCategory是一个属性而printQueue是预期值被分配到Active Directory中的打印机资源。类似地查询所有打印机开始字符'G'的LDAP查询(&(objectCategory属性的PrintQueue)(= G *))在上面的过滤器观察到的值没有引号('或“)在他们周围。

使用代码

示范项目,示范如何查询Active Directory服务,并获取不同的对象。LDAP查询和使用。NET类使用仅限于QueryObjectsByNETClasses()GetFilterString()方法。

下面的代码在QueryObjectsByNETClasses()方法创建了一个的DirectorySearcher对象,并设置属性的搜索,根据用户的喜好的主要形式。不同性质的描述是在代码中的注释。只有“name”添加到DirectorySearcher类里的PropertiesToLoad属性,以节省时间,因为我们只关心在检索列表中返回的对象的名称和objectClass。

 

DirectorySearcher ds = new DirectorySearcher();
    ds.SearchRoot = new DirectoryEntry("");    
      // start searching from local domain
    ds.Filter = GetFilterString();        
      // get the LDAP filter string based on selections on the form
    ds.PropertyNamesOnly = true;        
      // this will get names of only those 
      // properties to which a value is set
    ds.PropertiesToLoad.Add("name");

    // (PageSize) Maximum number of objects 
    // the server will return per page
    // in a paged search. Default is 0, i.e. no paged search
    if (ObjsPerPage.Text.Length > 0) 
        ds.PageSize = Int32.Parse(ObjsPerPage.Text);

    // (ServerPageTimeLimit) the amount of time the server
    // should observe to search a page of results
    // default is -1, i.e. search indefinitely
    if (PageTimeLimit.Text.Length > 0) 
        ds.ServerPageTimeLimit = new TimeSpan((long)(Decimal.Parse(
            PageTimeLimit.Text) * TimeSpan.TicksPerSecond));

    // (SizeLimit) maximum number of objects the server 
    // returns in a search
    // default is 0 - interpreted as server 
    // set default limit of 1000 entries
    if (ObjsToFetch.Text.Length > 0) 
        ds.SizeLimit = Int32.Parse(ObjsToFetch.Text);

    // (ServerTimeLimit) amount of time that the server 
    // should observe in a search
    // default is -1 interpreted as server default limit of 120 seconds 
    if (TotalTimeLimit.Text.Length > 0) 
        ds.ServerTimeLimit = new TimeSpan((long)(Decimal.Parse(
           TotalTimeLimit.Text) * TimeSpan.TicksPerSecond));

    // (SearchScope) option to search one level or complete subtree
    // default is Subtree, so set this option only if oneLevel is selected
    if (searchOptionCB.SelectedIndex == 1)
        ds.SearchScope = SearchScope.OneLevel;

    // (CacheResults) property by default is true
    ds.CacheResults = CacheResultsCB.Checked;

    ds.ReferralChasing = ReferralChasingOption.None;

    if (SortResultsCB.Checked)
        ds.Sort = new SortOption("name", SortDirection.Ascending);

FormFilter()和GetFilterString()函数用于,形成LDAP查询字符串(见的交代这些字符串的格式在LDAP过滤字符串格式一节)。主要观察前放置&和|运算的名单。如果你对上面有疑问,可针对不同的对象,请参阅MSDNActive Directory架构下形成了一套完整的属性。

 

    // form a filter string for the search in LDAP format
    private string FormFilter(string objectCategory, string filter)
    {
        String result;
        result = String.Format("(&(objectCategory={0})(name={1}))", 
           objectCategory, filter);
        return result;
    }

    // this function forms the filter string based on the selected
    // objects on the form
    private string GetFilterString()
    {
        // form the filter string for directory search
        string filter = "";
        if (UsersCB.Checked)
            filter += FormFilter("user", UsersFilter.Text);
        if (ComputersCB.Checked)
            filter += FormFilter("computer", ComputersFilter.Text);
        if (PrintersCB.Checked)
            filter += FormFilter("printQueue", PrintersFilter.Text);

        // add all the above filter strings
        return "(|" + filter + ")";
    }

 

要点及注意事项

  • 使用 objectCategory属性 对象类的 属性,而不是在有可能的情况下。Active Directory文档中提到这个问题相关的两件事情:
    • objectClass的属性可以有多个值。这可能是一个问题,特别是如果你retriving的对象类您可以有多个值!
    • objectCategory属性是一个索引属性,在Active Directory中。因此,使用objectCategory属性加快查询速度。

第二点是更重要的,因为所有的例子中给出MSDN使用的objectClass,而使用objectCategoryProperty将加快查询!

  • 如果列表查询过大则有可能超时。所以,不要感到惊讶,如果你的查询不返回完整的列表。有一点要注意的是,你不能设置一个的价值, ServerTimeLimit 大于120秒的默认值!所以,如果你正在寻找的所有对象和目录过大,最好是查询的次数,通过增量改变您的LDAP过滤字符串(为了如A *,B * ..)相结合的结果。
  • 尝试使用 PropertiesToLoad PropertyNamesOnly 性能 的DirectorySearcher, 如果你知道你是什么样的属性,试图检索。如果 PropertyNamesOnly 设置为true,则查询将获取这些属性的值被设置的名称。点名道姓属性是可以加载到 PropertiesToLoad中的 将减少读取时间。默认情况下 PropertiesToLoad 设置为一个空的 StringCollection中 获取的所有属性,并 PropertyNamesOnly 设置为false来检索所有属性的名称,即使没有设置一个值。对于如。在我的演示,我要加载的“名称”属性,并设置 PropertyNamesOnly 为true。请注意,即使没有指定 的objectClass objectCategory属性 有财产被自动加载,当一个对象被取出。
  • 默认情况下,所有的Active Directory中获取的结果会被缓存。设置的 CacheResults 财产 的DirectorySearcher, 为false刷新对象缓存在本地计算机上。

 

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值