【问题标题】:Validate credentials for remote domain验证远程域的凭据
【发布时间】:2021-08-10 08:35:33
【问题描述】:

谁能建议如何在远程域上验证凭据?

我的环境有多个域,它们之间没有定义信任关系。 我有一个 Powershell 脚本,它需要访问驻留在另一个域中的服务器上的共享文件夹,这显然需要身份验证。在访问它之前,我需要验证凭据以避免锁定(该脚本可以针对多个服务器运行)。

过去我使用过这个wonderful script,它使用当前域进行验证,但我无法让它在远程域上工作。 我试过这是(从上面的链接稍微修改的脚本):

function Test-Cred {
           
    [CmdletBinding()]
    [OutputType([String])] 
       
    Param ( 
        [Parameter( 
            Mandatory = $false, 
            ValueFromPipeLine = $true, 
            ValueFromPipelineByPropertyName = $true
        )] 
        [Alias( 
            'PSCredential'
        )] 
        [ValidateNotNull()] 
        [System.Management.Automation.PSCredential]
        [System.Management.Automation.Credential()] 
        $Credentials
    )
    $Domain = $null
    $Root = $null
    $Username = $null
    $Password = $null
      
    If($Credentials -eq $null)
    {
        Try
        {
            $Credentials = Get-Credential "domain\$env:username" -ErrorAction Stop
        }
        Catch
        {
            $ErrorMsg = $_.Exception.Message
            Write-Warning "Failed to validate credentials: $ErrorMsg "
            Pause
            Break
        }
    }
      
    # Checking module
    Try
    {
        # Split username and password
        $Username = $credentials.username
        $Password = $credentials.GetNetworkCredential().password
  
        # Get Domain
        ###$Root = "LDAP://" + ([ADSI]'').distinguishedName
        $Root = "LDAP://DC=remote_domain,DC=com"      ### statically define the remote domain
        $Domain = New-Object System.DirectoryServices.DirectoryEntry($Root,$UserName,$Password)
    }
    Catch
    {
        $_.Exception.Message
        Continue
    }
  
    If(!$domain)
    {
        Write-Warning "Something went wrong"
    }
    Else
    {
        If ($domain.name -ne $null)
        {
            return "Authenticated"
        }
        Else
        {
            $Domain    ### diagnosing the error
            return "Not authenticated"
        }
    }
}

我收到以下错误:

format-default : The following exception occurred while retrieving member "distinguishedName": "The user name or
password is incorrect.
"
    + CategoryInfo          : NotSpecified: (:) [format-default], ExtendedTypeSystemException
    + FullyQualifiedErrorId : CatchFromBaseGetMember,Microsoft.PowerShell.Commands.FormatDefaultCommand

用户名/密码 100% 正确。 谢谢

编辑 1

我找到了以下blog post,其中介绍了如何使用 .Net 程序集处理 Active Directory。以下效果很好

Add-Type -AssemblyName System.DirectoryServices.AccountManagement
#store credentials (of account with appropriate permissions)
$creds = Get-Credential 
#set the domain name
$dn = 'contoso.com' 

#Create the principal context object (so to say connect to a domain with the credentials provided)
$pc = [System.DirectoryServices.AccountManagement.PrincipalContext]::new([System.DirectoryServices.AccountManagement.ContextType]::`
Domain,$dn,$($creds.UserName),$($creds.GetNetworkCredential().Password))

我假设我可以在 If 语句中使用它来实现我所需要的。诚然,我不知道 .Net 的方式,它有点吓人,但我必须学习它。

编辑 2

这是我拼凑的:

Function Test-Cred
{
    [CmdletBinding()]
    [OutputType([String])] 
       
    Param ( 
        [Parameter( 
            Mandatory = $false, 
            ValueFromPipeLine = $true, 
            ValueFromPipelineByPropertyName = $true
        )] 
        [Alias( 
            'PSCredential'
        )] 
        [ValidateNotNull()] 
        [System.Management.Automation.PSCredential]
        [System.Management.Automation.Credential()] 
        $Credentials
    )
    
    Add-Type -AssemblyName System.DirectoryServices.AccountManagement      

    # Checking module

    $Validated = [System.DirectoryServices.AccountManagement.PrincipalContext]::new([System.DirectoryServices.AccountManagement.ContextType]::Domain,'remote_domain',$($Credentials.UserName),$($Credentials.GetNetworkCredential().Password))
 
    If ($Validated.ConnectedServer)
    {
        Return "Authenticated"
    }
    Else
    {
        Return "Not authenticated"
    }
}

有什么反馈吗?

编辑 3

嗯,EDIT 2 不适用于 Powershell 4,grrr

Method invocation failed because [System.DirectoryServices.AccountManagement.PrincipalContext] dies not contain method named 'new'

我必须让它像这样工作:

$ContextType = [System.DirectoryServices.AccountManagement.ContextType]::Domain
$ContextName = 'target_domain.com'
$Validated = New-Object -TypeName System.DirectoryServices.AccountManagement.PrincipalContext -ArgumentList $ContextType, $ContextName, $($Credentials.UserName),$($Credentials.GetNetworkCredential().Password)

【问题讨论】:

  • 请注意,不需要第一个 try/catch 块。 Get-Credential 不验证任何内容。它只是创建一个凭证对象,其中包含一个用户名字符串和一个安全字符串密码以供以后使用。它没有在该 try 块中进行测试、验证、使用等。
  • 好点!谢谢

标签: powershell active-directory ldap


【解决方案1】:

这是我的这个测试函数的最终版本,它适用于早于 5.1 的 Powershell 版本。

Function Test-Cred
    {
        [CmdletBinding()]
        [OutputType([String])] 
           
        Param ( 
            [Parameter( 
                Mandatory = $false, 
                ValueFromPipeLine = $true, 
                ValueFromPipelineByPropertyName = $true
            )] 
            [Alias( 
                'PSCredential'
            )] 
            [ValidateNotNull()] 
            [System.Management.Automation.PSCredential]
            [System.Management.Automation.Credential()] 
            $Credentials
        )
        
        # Checking module
        
        Add-Type -AssemblyName System.DirectoryServices.AccountManagement      

        $ContextType = [System.DirectoryServices.AccountManagement.ContextType]::Domain
        $ContextName = 'remote_domain.com'
        $Validated = New-Object -TypeName System.DirectoryServices.AccountManagement.PrincipalContext -ArgumentList $ContextType, $ContextName, $($Credentials.UserName),$($Credentials.GetNetworkCredential().Password)       
        If ($Validated.ConnectedServer)
        {
            Return "Authenticated"
        }
        Else
        {
            Return "Not authenticated"
        }
    }

【讨论】:

  • 嗨@Norski,你找到c#等效的吗?仅供参考。类 AccountManagement 可能不适用于只读 AD。在这种情况下使用 DirectoryServices.DirectoryEntry
猜你喜欢
  • 1970-01-01
  • 2010-09-24
  • 1970-01-01
  • 1970-01-01
  • 2014-08-24
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多