"Invoke -Command"로 명령의 반환 코드 포획 -PowerShell 2
-
06-07-2019 - |
문제
"Invoke-Command"를 사용하여 원격 시스템에서 스크립트를 실행하고 있습니다.
invoke-command -computername <server_name> -scriptblock {command to execute the script}
내 스크립트가 오류가있을 때 "-1"을 반환합니다. 따라서 리턴 코드를 확인하여 스크립트가 성공적으로 실행되었는지 확인하고 싶었습니다.
나는 다음과 같이 시도했다.
$code = invoke-command -computername ....
그러나 그것은 아무것도 반환하지 않습니다.
그렇지 않습니다 Invoke-command
스크립트 블록의 반환 코드를 잡으시겠습니까?
이것을 해결하는 다른 방법이 있습니까?
해결책
다른 서버에서 그러한 방식으로 명령을 실행하면 스크립트의 리턴 코드를 얻을 수있는 방법이 없다고 생각합니다. 이 때문입니다 Invoke-Command
원격 시스템에서 하나의 명령을 실행하면 단일 임시 세션 내에서 해당 세션에 다시 연결할 수 없습니다.
당신이 ~할 수 있다 그러나 원격 컴퓨터에서 세션을 만들고 해당 세션 내에서 스크립트를 호출하는 것입니다. 그 후 해당 세션에서 반환 값을 다시 확인할 수 있습니다. 그래서 라인을 따라 무언가 :
$s = New-PSSession -ComputerName <server_name>
Invoke-Command -Session $s -ScriptBlock { ... }
Invoke-Command -Session $s -ScriptBlock { $? }
작동 할 수도 있습니다. 이렇게하면 첫 번째 상태와 동일한 상태 및 변수에 액세스 할 수 있습니다. Invoke-Command
원격 기계에서.
또한 Invoke-Command
원격 명령의 리턴 값을 통과하지는 못할 것입니다. 그때 어떻게 알아낼까요? Invoke-Command
그 자체가 실패 했습니까?
ETA : 좋아, "반환 코드"와 관련하여 당신을 잘못 읽었습니다. 나는 당신이 의미한다고 가정했습니다 $?
. 어쨌든 문서에 따르면 다음과 같이 원격 컴퓨터에서 스크립트를 실행할 수 있습니다.
원격 컴퓨터에서 로컬 스크립트를 실행하려면
FilePath
매개 변수Invoke-Command
.예를 들어, 다음 명령이 실행됩니다
Sample.ps1
스크립트S1
그리고S2
컴퓨터 :invoke-command -computername S1, S2 -filepath C:\Test\Sample.ps1
스크립트의 결과는 로컬 컴퓨터로 반환됩니다. 파일을 복사 할 필요가 없습니다.
다른 팁
여기 예입니다 ...
원격 스크립트 :
try {
... go do stuff ...
} catch {
return 1
exit
}
return 2
exit
로컬 대본 :
function RunRemote {
param ([string]$remoteIp, [string]$localScriptName)
$res = Invoke-Command -computername $remoteIp -UseSSL -Credential $mycreds -SessionOption $so -FilePath $localScriptName
return $res
}
$status = RunRemote $ip_name ".\Scripts\myRemoteScript.ps1"
echo "Return status was $status"
$, -usessl 및 $ mycreds는 신탁 그룹 내부에 있다면 필요하지 않습니다. 이것은 나를 위해 일하는 것 같습니다 ... 행운을 빕니다!
원격 스크립트 블록이 종료 코드를 반환하면 PSESSION이 닫힙니다. 나는 단지 psession의 상태를 확인하고 있습니다. 닫히면 오류가 발생한다고 가정합니다. 일종의 해킹이지만 내 목적에 맞습니다.
$session = new-pssession $env:COMPUTERNAME
Invoke-Command -ScriptBlock {try { ErrorHere } Catch [system.exception] {exit 1}} -Session $session
if ($session.State -eq "Closed")
{
"Remote Script Errored out"
}
Remove-PSSession $session
$session = new-pssession $env:COMPUTERNAME
Invoke-Command -ScriptBlock {"no exitcodes here"} -Session $session
if ($session.State -ne "Closed")
{
"Remote Script ran succesfully"
}
Remove-PSSession $session
Invoke-Command를 통해 불리는 배치 스크립트로 오류 코드 리턴을 포착하려고했습니다. 쉬운 일은 아니지만 나는 그것을 할 수있는 멋지고 쉬운 방법을 찾았습니다.
당신은 PowerShell 스크립트입니다$res=invoke-command -Computername %computer% {C:\TEST\BATCH.CMD}
write-host $res
$ res가 배치 출력임을 알게 될 것입니다. @echo off,> nul 및 echo "반품하고 싶은 것"을 사용하여 이것을 알고 있습니다!
당신은 스크립트를 배치합니다
@echo off
echo "Start Script, do not return" > nul
echo 2
이제 $ res는 = 2입니다! 그런 다음 배치에 모든 논리를 적용 할 수 있습니다.
Invoke-Command -Asjob을 사용하여 수신 작업을 사용하여 출력을 얻을 수도 있습니다! 이 경우 $ res를 사용할 필요가 없습니다.
건배, Julien
마지막 PowerShell은 아래에 오류 코드가 실행 된 스크립트에서 0이고 반환 코드가 0이 아닌 경우 부울 False 인 경우 부울 true를 반환합니다. 원격 실행에서 반환 된 오류 코드를 감지하는 데 적합합니다.
function executeScriptBlock($scriptString) {
Write-Host "executeScriptBlock($scriptString) - ENTRY"
$scriptBlock = [scriptblock]::Create($scriptString + " `n " + "return `$LASTEXITCODE")
Invoke-Command -Session $session -ScriptBlock $scriptBlock
$rtnCode = Invoke-Command -Session $session -ScriptBlock { $? }
if (!$rtnCode) {
Write-Host "executeScriptBlock - FAILED"
}
Else {
Write-Host "executeScriptBlock - SUCCESSFUL"
}
}
스크립트 블록에서 출력이 필요한 경우 그리고 종료 코드는 블록에서 종료 코드를 던져 통화 쪽의 정수로 다시 변환 할 수 있습니다 ...
$session = new-pssession $env:COMPUTERNAME
try {
Invoke-Command -ScriptBlock {Write-Host "This is output that should not be lost"; $exitCode = 99; throw $exitCode} -Session $session
} catch {
$exceptionExit = echo $_.tostring()
[int]$exceptionExit = [convert]::ToInt32($exceptionExit)
Write-Host "`$exceptionExit = $exceptionExit"
}
이렇게하면 표준 출력 및 마지막 출구 코드가 반환됩니다. 그러나 스크립트 블록 내에서 예외는 출구 코드로 포착되어 재발해야합니다. 예제에서 출력 ...
This is output that should not be lost
$exceptionExit = 99