域环境通过powershell 远程修改本地管理员账户密码
function Invoke-PasswordRoll{
Param(
]
$ComputerName,
]
$LocalAccounts,
$TsvFileName,
$EncryptionKey,
$PasswordLength = 20,
$NoEncryption
)
#加载任何所需的 .net 类
Add-Type -AssemblyName "System.Web" -ErrorAction Stop
#这是脚本块,将在 ComputerName 中指定的每台计算机上执行
$RemoteRollScript = {
Param(
]
$Passwords,
]
$LocalAccounts,
#在此处,我可以记录脚本所连接到的服务器名称,DNS 记录有时会变得很混乱,现在这样非常好。
$TargettedServerName
)
$LocalUsers = Get-WmiObject Win32_UserAccount -Filter "LocalAccount=true" | Foreach {$_.Name}
#检查计算机是否具有密码不会由此脚本滚动的任何本地用户帐户
foreach ($User in $LocalUsers)
{
if ($LocalAccounts -inotcontains $User)
{
Write-Warning "Server: '$($TargettedServerName)' has a local account '$($User)' whos password is NOT being changed by this script"
}
}
#对于此服务器中存在的所有指定的本地帐户,更改密码
$PasswordIndex = 0
foreach ($LocalAdmin in $LocalAccounts)
{
$Password = $Passwords[$PasswordIndex]
if ($LocalUsers -icontains $LocalAdmin)
{
try
{
$objUser = "WinNT://localhost/$($LocalAdmin), user"
$objUser.psbase.Invoke("SetPassword", $Password)
$Properties = @{
TargettedServerName = $TargettedServerName
Username =$LocalAdmin
Password = $Password
RealServerName = $env:computername
}
$ReturnData = New-Object PSObject -Property $Properties
Write-Output $ReturnData
}
catch
{
Write-Error "Error changing password for user:$($LocalAdmin) on server:$($TargettedServerName)"
}
}
$PasswordIndex++
}
}
#在运行此脚本的客户端上生成密码,而非在远程计算机上。.NET 客户端配置文件中不提供 System.Web.Security。在运行该脚本的 # 客户端上进行此调用可确保只有 1 台计算机需要安装完整的 .NET 运行库(相对于已滚动密码的每个系统)。
function Create-RandomPassword
{
Param(
$PasswordLength
)
$Password = ::GeneratePassword($PasswordLength, $PasswordLength / 4)
#此操作绝对不会失败,但不管怎样,我还是在这里加入了健全性检查
if ($Password.Length -ne $PasswordLength)
{
throw new Exception("Password returned by GeneratePassword is not the same length as required. Required length: $($PasswordLength). Generated length: $($Password.Length)")
}
return $Password
}
#主要功能 - 生成密码并通过远程方式进入计算机以更改指定的本地帐户的密码
if ($PsCmdlet.ParameterSetName -ieq "Encryption")
{
try
{
$Sha256 = new-object System.Security.Cryptography.SHA256CryptoServiceProvider
$SecureStringKey = $Sha256.ComputeHash(::Unicode.GetBytes($EncryptionKey))
}
catch
{
Write-Error "Error creating TSV encryption key" -ErrorAction Stop
}
}
foreach ($Computer in $ComputerName)
{
#需要为每个帐户生成 1 个可以更改的密码
$Passwords = @()
for ($i = 0; $i -lt $LocalAccounts.Length; $i++)
{
$Passwords += Create-RandomPassword -PasswordLength $PasswordLength
}
Write-Output "Connecting to server '$($Computer)' to roll specified local admin passwords"
$Result = Invoke-Command -ScriptBlock $RemoteRollScript -ArgumentList @($Passwords, $LocalAccounts, $Computer) -ComputerName $Computer
#如果正在使用加密,则在写入磁盘之前,使用用户提供的密钥对密码进行加密
if ($Result -ne $null)
{
if ($PsCmdlet.ParameterSetName -ieq "NoEncryption")
{
$Result | Select-Object Username,Password,TargettedServerName,RealServerName | Export-Csv -Append -Path $TsvFileName -NoTypeInformation
}
else
{
#筛选掉返回的 $null 条目
$Result = $Result | Select-Object Username,Password,TargettedServerName,RealServerName
foreach ($Record in $Result)
{
$PasswordSecureString = ConvertTo-SecureString -AsPlainText -Force -String ($Record.Password)
$Record | Add-Member -MemberType NoteProperty -Name EncryptedPassword -Value (ConvertFrom-SecureString -Key $SecureStringKey -SecureString $PasswordSecureString)
$Record.PSObject.Properties.Remove("Password")
$Record | Select-Object Username,EncryptedPassword,TargettedServerName,RealServerName | Export-Csv -Append -Path $TsvFileName -NoTypeInformation
}
}
}
}
}function ConvertTo-CleartextPassword
{
页:
[1]