简体   繁体   English

Active Directory无法在C#中查找所有用户

[英]Active Directory not finding all users in C#

I have some code that queries Active Directory to verify user existence. 我有一些查询Active Directory以验证用户存在的代码。 I am trying to verify a long list of about 1300 ids. 我正在尝试验证大约1300个ID的长列表。 I've tried several methods to verify if a user account (LINQ to AD, DirectorySearcher (with and without a parent DirectoryEntry) and also a DirectoryEntry that links to the WinNT:// path). 我已经尝试了几种方法来验证用户帐户(LINQ to AD,DirectorySearcher(有和没有父DirectoryEntry)以及链接到WinNT://路径的DirectoryEntry)。 Every time it will come back and say that several users do not exist. 每次它会回来并说几个用户不存在。 If I hardcode their userids in the code and execute for individually, it validates existence. 如果我在代码中对其用户ID进行硬编码并单独执行,则会验证是否存在。 If I try and do it in a foreach loop, I get several false negatives. 如果我尝试在foreach循环中执行此操作,我会得到几个漏报。

Here's the code I am using right now.. 这是我现在使用的代码..

static string[] userIDs = new string[] "user1","user2","user3","user4","user5","user6","user7","user8"...,"user1300"};

List<string> nonExistingUsers = new List<string>();
List<string> ExistingUsers = new List<string>();
foreach (string s in userIDs)
{
 DirectorySearcher search = new DirectorySearcher();
 search.Filter = String.Format("(SAMAccountName={0})", s);
 search.PropertiesToLoad.Add("cn");
 DirectorySearcher ds = new DirectorySearcher(de, "(&(objectClass=user)(cn=" + s + "))", new string[] { "Name" }, SearchScope.Subtree);
 SearchResultCollection resultCollection = ds.FindAll();
 SearchResult result = search.FindOne();
 if (result != null)
  ExistingUsers.Add(s);
 else
  nonExistingUsers.Add(s);
}

Any suggestions or reasons why I am getting the false negatives? 我得到假阴性的任何建议或理由?

Couple of things: 几件事:

  • first of all, try using the "anr=" (ambiguous name resolution) in your LDAP filter - it searches several name-related attributes and make searching easier. 首先,尝试在LDAP过滤器中使用“anr =”(模糊名称解析) - 它会搜索多个与名称相关的属性并使搜索更容易。 The UserID might not be part of the actual "common name" (CN=user1) UserID可能不是实际“通用名称”的一部分(CN = user1)

  • secondly, use the objectCategory instead of objectClass - the objectCategory is single-valued and indexed and thus a fair bit faster on searches 其次,使用objectCategory而不是objectClass - objectCategory是单值的并且索引,因此在搜索上更快一点

  • thirdly: why are you first calling .FindAll() and then .FindOne() on the next line? 第三:你为什么先在下一行调用.FindAll()然后调用.FindOne()? Doesn't seem really necessary at all.... 似乎没有必要......

  • WinNT:// really is only for backward compatibility and if you need to deal with local computer accounts - try to avoid it whenever possible, it also exposes a lot less properties than LDAP WinNT://实际上只是为了向后兼容,如果你需要处理本地计算机帐户 - 尽可能避免使用它,它还会暴露比LDAP更少的属性

Here's my code I'd write: 这是我写的代码:

static string[] userIDs = new string[] "user1","user2","user3","user4","user5","user6","user7","user8"...,"user1300"};

DirectoryEntry searchRoot = new DirectoryEntry("LDAP://cn=Users,dc=YourComp,dc=com");

List<string> nonExistingUsers = new List<string>();
List<string> ExistingUsers = new List<string>();

foreach (string s in userIDs)
{
   DirectorySearcher search = new DirectorySearcher(searchRoot);

   search.SearchScope = SearchScope.Subtree;
   search.Filter = string.Format("(&(objectCategory=person)(anr={0}))", s);

   SearchResultCollection resultCollection = ds.FindAll();

   if(resultCollection != null && resultCollection.Count > 0)
      ExistingUsers.Add(s);
   else
      nonExistingUsers.Add(s);
}

Does that work in your scenario?? 这在你的场景中有用吗?

Also, if you're using .NET 3.5 or higher, things got a lot easier - see: 此外,如果您使用的是.NET 3.5或更高版本,则事情变得更加容易 - 请参阅:

Managing Directory Security Principals in the .NET Framework 3.5 管理.NET Framework 3.5中的目录安全性主体

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM