如何从C#中的显示名称获取Active Directory中的用户名?

时间:2012-03-23 19:33:55

标签: c# .net active-directory

我希望能够使用该用户的显示名称获取Active Directory中用户的用户标识。显示名称是从数据库中获取的,并且在该用户会话期间使用以下代码存储以获取显示名称:

using System.DirectoryServices.AccountManagement;

    private string GetDisplayName()
    {
        // set up domain context
        PrincipalContext ctx = new PrincipalContext(ContextType.Domain);

        // find currently logged in user
        UserPrincipal user = UserPrincipal.Current;

        return user.DisplayName;
    }

这一次,我希望有一个名为GetUserIdFromDisplayName()的方法,它返回Active Directory登录名。有什么想法吗?

2 个答案:

答案 0 :(得分:32)

我相信通过使用System.DirectoryServices.AccountManagement(S.DS.AM)命名空间的内置功能,您可以比使用David的答案更容易做到这一点。

基本上,您可以定义域上下文并轻松在AD中查找用户和/或组:

using System.DirectoryServices.AccountManagement;

private string GetUserIdFromDisplayName(string displayName)
{
    // set up domain context
    using(PrincipalContext ctx = new PrincipalContext(ContextType.Domain))
    {
        // find user by display name
        UserPrincipal user = UserPrincipal.FindByIdentity(ctx, displayName);

        // 
        if (user != null)
        {
             return user.SamAccountName;
             // or maybe you need user.UserPrincipalName;
        }
        else
        {
             return string.Empty;
        }
    }
}

我认为没有必要去基础的DirectoryEntry对象,除非UserPrincipal的所有属性都不是您正在寻找的。

PS:如果按显示名称搜索不起作用(我手边没有AD来测试它) - 您也可以随时使用PrincipalSearcher找到您的用户:

using System.DirectoryServices.AccountManagement;

private string GetUserIdFromDisplayName(string displayName)
{
    // set up domain context
    using(PrincipalContext ctx = new PrincipalContext(ContextType.Domain))
    {
        // define a "query-by-example" principal - here, we search for a UserPrincipal 
        // and with the display name passed in
        UserPrincipal qbeUser = new UserPrincipal(ctx);
        qbeUser.DisplayName = displayName;

        // create your principal searcher passing in the QBE principal    
        PrincipalSearcher srch = new PrincipalSearcher(qbeUser);

        // find match - if exists
        UserPrincipal user = srch.FindOne() as UserPrincipal;

        if (user != null)
        {
             return user.SamAccountName;
             // or maybe you need user.UserPrincipalName;
        }
        else
        {
             return string.Empty;
        }
    }
}

答案 1 :(得分:8)

UserPrincipalGetUnderlyingObject()方法会返回DirectoryEntry

从Principal获取DirectoryEntry:

private DirectoryEntry GetDirectoryEntryFromUserPrincipal(Principal user)
{
    return (DirectoryEntry)user.GetUnderlyingObject();
}

从域名和帐户名称获取DirectoryEntry:

private DirectoryEntry GetDirectoryEntryFromDomainAndUsername(string domainName, string userName)
{
    // Get the sid from the NT account name
    var sid = (SecurityIdentifier) new NTAccount(domainName, accountName)
                  .Translate(typeof(SecurityIdentifier));

    // Get the directory entry for the LDAP service account
    var serviceEntry = new DirectoryEntry("LDAP://{address}", "serviceUsername", "servicePassword");

    var mySearcher = new DirectorySearcher(serviceEntry)
        {
            Filter = string.Format("(&(ObjectSid={0}))", sid.Value)
        };

    return mySearcher.FindOne().GetDirectoryEntry();
}

DirectoryEntry使用Guid属性获取条目Object-Guid

private Guid GetObjectGuidFromDirectoryEntry(DirectoryEntry entry)
{
    // return the Guid this is the Object-Guid (ignore NativeGuid)
    return entry.Guid;
}

使用目录帐户跟踪应用程序中的用户帐户:始终使用Object-Guid作为“创建对象时无法更改此值。”
如果用户更改域名,或者更常见的是更改其姓名(婚姻,合法姓名更改等),则NT和SAM帐户名称可能会更改,并且不应用于跟踪用户。

获取NT帐户名称(域\用户名):

private string GetNTAccountNameFromDirectoryEntry(DirectoryEntry entry)
{
    PropertyValueCollection propertyValueCollection = entry.Properties["objectsid"];

    SecurityIdentifier sid = new SecurityIdentifier((byte[]) propertyValueCollection[0], 0);

    NTAccount ntAccount = (NTAccount)sid.Translate(typeof (NTAccount));

    return account.ToString();
}

获取SAM帐户名称(用户名@域名):

private string GetSAMAccountFromDirectoryEntry(DirectoryEntry entry)
{
    return entry.Properties["Name"].Value;
}

这是所有Active Directory属性的exhaustive list。从Properties获取值时,请使用“Ldap-Display-Name” 例如Properties["Ldap-Display-Name"]

Display-Name(FirstName MI LastName)可能派上用场。