web-dev-qa-db-ja.com

リモートコンピューターで.regファイルを実行するためのPowerShellスクリプト

PsExecを使用してバッチファイルを作成してリモートコンピューターのレジストリ設定を更新しようとしましたが成功しなかったので、Powershellを使用しようとしています。 Googleを使用し、さまざまなフォーラムで入手可能なスクリプトを試して、次のスクリプトをコンパイルしました。

 $myWindowsID=[System.Security.Principal.WindowsIdentity]::GetCurrent()
 $myWindowsPrincipal=new-object System.Security.Principal.WindowsPrincipal($myWindowsID)


 $adminRole=[System.Security.Principal.WindowsBuiltInRole]::Administrator


 if ($myWindowsPrincipal.IsInRole($adminRole))
    {

    $Host.UI.RawUI.WindowTitle = $myInvocation.MyCommand.Definition + "(Elevated)"
    $Host.UI.RawUI.BackgroundColor = "Darkred"
    clear-Host
    }
 else
    {


    $newProcess = new-object System.Diagnostics.ProcessStartInfo "PowerShell";


    $newProcess.Arguments = $myInvocation.MyCommand.Definition;


    $newProcess.Verb = "runas";


    [System.Diagnostics.Process]::Start($newProcess);


    exit
    }

winrm quickconfig


    $servers = Get-Content c:\temp\servers.txt


    $HostedRegFile = "temp\OfficeDocumentfix.reg"

    foreach ($server in $servers)

    {

    $newfile = "\\$servers\c`$\Downloads\RegistryFiles\"

    New-Item -ErrorAction SilentlyContinue -ItemType directory -Path \\$servers\C$\Downloads\RegistryFiles\

    Copy-Item $HostedRegFile -Destination $newfile

    Invoke-Command -ComputerName $server -ScriptBlock {

    Start-Process -filepath "C:\windows\regedit.exe" -argumentlist "/s C:\Downloads\RegistryFiles\test.reg"



 Write-Host -NoNewLine "Press any key to continue..."
 $null = $Host.UI.RawUI.ReadKey("NoEcho,IncludeKeyDown")

$returncode = $?+":"+$lastexitcode;

$codearr = $returncode.split(":");

write-Host $codearr[0];

write-Host $codearr[1];

#echo Registry_updated_successfully

#:Failed
#echo Registry_update_failed

 Write-Host -NoNewLine "Press any key to continue..."
 $null = $Host.UI.RawUI.ReadKey("NoEcho,IncludeKeyDown")
 }

 }

私の問題では、スクリプトを実行すると、次のエラーが発生します

WinRMは、このマシンで要求を受信するように既に設定されています。

WinRMは、このマシンのリモート管理用にすでにセットアップされています。

コピー項目:パス 'C:\ OfficeDocumentfix.reg'が存在しないため、見つかりません。

しかし、パスは正しいです。私が使用しているスクリプトに明らかに明らかに間違っているものがあります。これは、Powershellへの2回目のプッシュです。

2
Paul508

WinRMは、このマシンで要求を受信するように既に設定されています。

WinRMは、このマシンのリモート管理用にすでにセットアップされています。

この_winrm quickconfig_をスクリプトから削除します。 WinRMサービスを構成する必要がありますが、すでにセットアップされているため、これは必要ありません。 WinRMを使用すると、サービスを介してリモートコンピューターにアクセスできます。たとえば、_invoke-command {}_に必要です。

コピー項目:パス 'C:\ OfficeDocumentfix.reg'が存在しないため、見つかりません。

その理由は、あなたの_$newfile_変数は、必要に応じて_$servers_ではなく_$server_を使用するためです(foreach()ブロック内にあるため)_$servers_は_$null_です。それがエラーの原因です。

使用しているレジストリファイルがHKCU:に書き込む場合、スクリプトを昇格する必要はありません。HKLMに書き込む場合:昇格する必要があります。管理者のみがHKLMに書き込むことができます。標高は、最初から_winrm quickconfig_までの全体です。

これにより、次の最終製品が得られるはずです(私はそこに標高を残しました):

_$myWindowsID=[System.Security.Principal.WindowsIdentity]::GetCurrent()
$myWindowsPrincipal=new-object System.Security.Principal.WindowsPrincipal($myWindowsID)

$adminRole=[System.Security.Principal.WindowsBuiltInRole]::Administrator

if ($myWindowsPrincipal.IsInRole($adminRole))
{
    $Host.UI.RawUI.WindowTitle = $myInvocation.MyCommand.Definition + "(Elevated)"
    $Host.UI.RawUI.BackgroundColor = "Darkred"
    clear-Host
}
else
{
    $newProcess = new-object System.Diagnostics.ProcessStartInfo "PowerShell";
    $newProcess.Arguments = $myInvocation.MyCommand.Definition;
    $newProcess.Verb = "runas";
    [System.Diagnostics.Process]::Start($newProcess);
    exit
}

$servers = Get-Content c:\temp\servers.txt

$HostedRegFile = "C:\temp\CyclopsOfficeDocumentfix.reg"
foreach ($server in $servers)
{
    $newfile = "\\$server\c`$\Downloads\RegistryFiles\"
    New-Item -ErrorAction SilentlyContinue -ItemType directory -Path \\$server\C$\Downloads\RegistryFiles\
    Copy-Item $HostedRegFile -Destination $newfile
    Invoke-Command -ComputerName $server -ScriptBlock {
        Start-Process -filepath "C:\windows\regedit.exe" -argumentlist "/s C:\Downloads\RegistryFiles\test.reg"
        Write-Host -NoNewLine "Press any key to continue..."
    }
}
_

この行も見てください:

_Start-Process -filepath "C:\windows\regedit.exe" -argumentlist "/s C:\Downloads\RegistryFiles\test.reg"
_

まだ動的ではありません。希望するregファイルではなく、常に_test.reg_で読み込まれます。

_start-process_の代わりに、単に_regedit /s $regfile /f_を使用することもできます。PowerShellはバッチのようなコマンドを実行できます(ただし、詳細です。このように機能する場合は、そのままにしておきます)。

4
SimonS

ダブルホップやその他の認証の問題を台無しにせず、レジストリファイルの内容をパラメータとしてInvoke-Commandに渡すことを好みます。これは、リモートサーバーがファイルをプルしようとしているどこかのファイル共有に到達しようとする場合に比べて、特定の利点を提供し、ドメインをまたがるコンピューターからでも実行できます。

$regFile = @"
Windows Registry Editor Version 5.00

[HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\services\Tcpip\Parameters]
"MaxUserPort"=dword:00005000
"TcpTimedWaitDelay"=dword:0000001e
"@

Invoke-Command -ComputerName comp -ScriptBlock {param($regFile) $regFile | out-file $env:temp\a.reg; 
    reg.exe import $env:temp\a.reg } -ArgumentList $regFile
2