首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >如何检查NTAccount对象是否代表组或用户?

如何检查NTAccount对象是否代表组或用户?
EN

Stack Overflow用户
提问于 2010-08-12 04:49:21
回答 2查看 4.7K关注 0票数 5

当使用由

代码语言:javascript
复制
GetAccessRules(True, True, GetType(System.Security.Principal.NTAccount))

如何判断每个规则中引用的NTAccount对象是用户帐户还是组?

更新:

我能够按以下方式解决这个问题。注意,如果True是一个组,则此代码的目的是返回NTAccount,如果NTAccount是一个组,则返回False,或者在检查过程中发生错误。

有更好的方法吗?

代码语言:javascript
复制
Public Function IsGroup(ByVal account As NTAccount) as Boolean  
    Dim samAccountName as string = account.Value  
    Dim accountNameParts() As String = samAccountName.Split("\")  
    If accountNameParts.Count() = 2 Then  
        Dim principalContext As PrincipalContext  
        Try  
            principalContext = New PrincipalContext(ContextType.Domain, accountNameParts(0))  
        Catch  
            Try  
                principalContext = New PrincipalContext(ContextType.Machine, accountNameParts(0))  
            Catch  
                principalContext = Nothing  
            End Try  
        End Try  
        If Not principalContext Is Nothing Then  
            Dim principal As Principal  
            principal = principal.FindByIdentity(principalContext, _samAccountName)  
            If Not principal Is Nothing then   
                return TypeOf principal Is GroupPrincipal  
            End If  
        End If  
    End If  
    Return False  
End Function

另一个更新:

上面的解决方案对于大多数服务器\帐户对象都是可以的,但是对于我们拥有的EMC Celerra服务器上的本地组对象来说,它失败了。我正在尝试使用NetUserGetInfo/NetLocalGroupGetInfo Win API调用来查看该调用是否有效,但我无法让它们正常工作。有关更多详细信息,请参阅NetUserGetInfo/NetLocalGroupGetInfo returning error 1722

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2011-06-08 02:34:27

解决这个问题的方法确实是使用Windows (NetUserGetInfoNetLocalGroupGetInfo)。

代码语言:javascript
复制
Class NetApi
    Private Declare Unicode Function NetUserGetInfo Lib "Netapi32.dll" ( _
         ByVal ServerName As String, _
         ByVal UserName As String, _
         ByVal level As Integer, _
         ByRef BufPtr As IntPtr) As Integer

    Private Declare Unicode Function NetLocalGroupGetInfo Lib "Netapi32.dll" ( _
         ByVal ServerName As String, _
         ByVal GroupName As String, _
         ByVal level As Integer, _
         ByRef BufPtr As IntPtr) As Integer

    Declare Unicode Function NetApiBufferFree Lib "netapi32.dll" _
    (ByRef buffer As IntPtr) As Long

    Public Shared Function PrincipalIsGroup(ByVal MachineName As String, ByVal AccountName As String) As String
        If String.IsNullOrEmpty(MachineName) Then
            Throw New ArgumentException("MachineName is Required")
        End If
        If String.IsNullOrEmpty(AccountName) Then
            Throw New ArgumentException("AccountName is Required")
        End If
        Dim returnValue As String = "NotFound"
        Dim bufPtr As IntPtr
        Dim lngReturn As Integer = NetLocalGroupGetInfo("\\" & MachineName, AccountName, 0, bufPtr)
        Call NetApiBufferFree(bufPtr)
        bufPtr = IntPtr.Zero
        If lngReturn = 0 Then
            returnValue = "True"
        Else
            lngReturn = NetUserGetInfo("\\" & MachineName, AccountName, 0, bufPtr)
            Call NetApiBufferFree(bufPtr)
            bufPtr = IntPtr.Zero
            If lngReturn = 0 Then
                returnValue = "False"
            End If
        End If
        Return returnValue
    End Function
End Class
票数 2
EN

Stack Overflow用户

发布于 2013-03-13 21:42:54

我遇到了和你一样的问题。在做了一些研究之后,我终于找到了一个不错的解决方案:使用WinAPI LookupAccountSid。我已经测试了这两个域和本地帐户。域\用户、NT授权\系统、MachineName\管理员都将工作。请注意,我没有将任何异常处理放在那里。您可以判断什么样的处理方式可以接受您的场景。要获得异常,可以使用System.Runtime.InteropServices.Marshal.GetLastWin32Error()

代码语言:javascript
复制
public enum PrincipalType
{
    User,
    Group
}
public bool TryGetPrincipalType(string domainQualifiedName, out PrincipalType type)
{
        var name = new StringBuilder();
        var cchName = (uint) name.Capacity;
        var referencedDomainName = new StringBuilder();
        var cchReferencedDomainName = (uint) referencedDomainName.Capacity;
        SID_NAME_USE sidType;

        var account = new NTAccount(domainQualifiedName);

        var id = new SecurityIdentifier(account.Translate(typeof (SecurityIdentifier)).Value);
        var sidBuffer = new byte[id.BinaryLength];
        id.GetBinaryForm(sidBuffer, 0);

        if (LookupAccountSid(null, sidBuffer, name, ref cchName, referencedDomainName,
                             ref cchReferencedDomainName, out sidType))
        {
            switch (sidType)
            {
                case SID_NAME_USE.SidTypeGroup:
                case SID_NAME_USE.SidTypeWellKnownGroup:
                case SID_NAME_USE.SidTypeAlias:
                    type = PrincipalType.Group;
                    return true;
                case SID_NAME_USE.SidTypeUser:
                    type = PrincipalType.User;
                    return true;
            }
        }
        type = default(PrincipalType);
        return false;
    }
private enum SID_NAME_USE
{
    SidTypeUser = 1,
    SidTypeGroup,
    SidTypeDomain,
    SidTypeAlias,
    SidTypeWellKnownGroup,
    SidTypeDeletedAccount,
    SidTypeInvalid,
    SidTypeUnknown,
    SidTypeComputer
}
[DllImport("advapi32.dll", CharSet = CharSet.Auto, SetLastError = true)]
private static extern bool LookupAccountSid(
        string lpSystemName,
        [MarshalAs(UnmanagedType.LPArray)] byte[] Sid,
        StringBuilder lpName,
        ref uint cchName,
        StringBuilder ReferencedDomainName,
        ref uint cchReferencedDomainName,
        out SID_NAME_USE peUse);
票数 4
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/3464821

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档