Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/security/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 如何检查域中是否存在Windows用户帐户名?_C#_Security - Fatal编程技术网

C# 如何检查域中是否存在Windows用户帐户名?

C# 如何检查域中是否存在Windows用户帐户名?,c#,security,C#,Security,在C#中,检查Windows用户帐户名是否存在的最简单、最有效的方法是什么?这是在域环境中 输入:以[domain]/[user]格式输入的用户名(例如“mycompany\bob”) 输出:如果用户名存在,则为True;如果不存在,则为false 我确实发现了一些与验证和操作用户帐户有关的示例,它们假设您已经有了一个用户可分辨名称,而我是从用户帐户名称开始的 我相信我可以用AD解决这个问题,但在我这么做之前,我想知道是否有一个简单的更高级别的API可以满足我的需要 *更新* 可能有很多方法

在C#中,检查Windows用户帐户名是否存在的最简单、最有效的方法是什么?这是在域环境中

  • 输入:以[domain]/[user]格式输入的用户名(例如“mycompany\bob”)
  • 输出:如果用户名存在,则为True;如果不存在,则为false
我确实发现了一些与验证和操作用户帐户有关的示例,它们假设您已经有了一个用户可分辨名称,而我是从用户帐户名称开始的

我相信我可以用AD解决这个问题,但在我这么做之前,我想知道是否有一个简单的更高级别的API可以满足我的需要

*更新*

可能有很多方法可以做到这一点,Russ发布了一个可行的方法,但我不知道如何调整它以在我的环境中工作。我确实找到了一种不同的方法,使用为我完成任务的WinNT提供程序:

    public static bool UserInDomain(string username, string domain)
    {
        string path = String.Format("WinNT://{0}/{1},user", domain, username);

        try
        {
            DirectoryEntry.Exists(path);
            return true;
        }
        catch (Exception)
        {
            // For WinNT provider DirectoryEntry.Exists throws an exception
            // instead of returning false so we need to trap it.
            return false;
        }
    }
附言。 对于那些不熟悉上面使用的API的人:需要添加对System.DirectoryServices的引用才能使用它

我找到的链接帮助我做到了这一点: 这些示例使用ADSI,但也可以应用于.NET DirectoryServices。它们还演示了可能有用的用户对象的其他属性。

本文中的名称空间正是您所需要并打算用于此目的的名称空间。如果我没记错的话,它是COM接口的包装器

编辑:

像下面这样的东西应该可以做到这一点(可能需要一些检查和处理)。它将使用当前安全上下文的域来查找域控制器,但可以很容易地将其修改为传入命名服务器

public bool UserInDomain(string username, string domain)
{
    string LDAPString = string.Empty;
    string[] domainComponents = domain.Split('.');
    StringBuilder builder = new StringBuilder();

    for (int i = 0; i < domainComponents.Length; i++)
    {
        builder.AppendFormat(",dc={0}", domainComponents[i]);
    }
    if (builder.Length > 0)
        LDAPString = builder.ToString(1, builder.Length - 1);

    DirectoryEntry entry = new DirectoryEntry("LDAP://" + LDAPString);

    DirectorySearcher searcher = new DirectorySearcher(entry);

    searcher.Filter = "sAMAccountName=" + username;

    SearchResult result = searcher.FindOne();

    return result != null;
}

如果您使用的框架版本足够高,找到了一种简单的方法:

using System.DirectoryServices.AccountManagement;

bool UserExists(string userName, string domain) {
    using (var pc = new PrincipalContext(ContextType.Domain, domain))
    using (var p = Principal.FindByIdentity(pc, IdentityType.SamAccountName, userName)) {
        return p != null;
    }
}

这些是用于访问Active Directory信息的通用API(如用于SQL数据的ADO.NET)。AD编程的挑战在于理解模式并构造正确的查询以获取所需信息(AD中存储了大量信息)。@DSO-您拥有域和用户名,因此,您应该能够使用DirectorySearcher对象,通过实例化DirectorySearcher对象并传递绑定到表示域对象的节点的DirectoryEntry对象,来查找该域中是否存在用户名。您的示例对我不起作用,我收到一个“服务器返回了引用”错误,我认为这意味着容器不存在。我认为您原则上是正确的,首先绑定到正确的容器,然后搜索对象,所以我给了您投票支持。但是,我不认为您构建绑定到域的查询的方法在所有环境中都有效。我找到了一个更简单的解决方案(更新后的帖子)。我在发帖前做了测试,它对我有效。您是为用户名传入完全限定的用户名,还是仅传入用户名?只有用户名才能超快速下载新版本,这正是我所需要的。谢谢
using System.DirectoryServices.AccountManagement;

bool UserExists(string userName, string domain) {
    using (var pc = new PrincipalContext(ContextType.Domain, domain))
    using (var p = Principal.FindByIdentity(pc, IdentityType.SamAccountName, userName)) {
        return p != null;
    }
}