簡體   English   中英

讓 pssessions 為 txt 文件中列出的多個服務器正確循環的問題

[英]Issue getting pssessions to loop properly for multiple servers listed in a txt file

我從一個名為 vms.txt 的 txt 文件開始。

它包含 2 個服務器,如下所示:

server1
server2

當我運行如下所示的腳本時,為安裝 VMware 工具而調用的命令僅在 server2 上運行,而 server1 被跳過。 有沒有人對如何修改此腳本以使其在 txt 文件中的兩台服務器上運行有任何建議? 將來我將不得不為數百個虛擬機運行它,所以我試圖找到一種簡單的方法讓它正確循環。

$cred = Get-Credential
$vms = Get-Content C:\Scripts\Tools\vms.txt

foreach($vm in $vms){
$sessions = New-PSSession -ComputerName $vm -Credential $cred
}

foreach($session in $sessions)
{
Invoke-Command -Session $session -ScriptBlock {
c:\users\jsmith\documents\VMware-tools-10.3.5.exe /v "/qn REBOOT=R Remove=AppDefense,VMCI”
}
} 

在基於循環的方法中,問題在於您的變量賦值

# !! This only ever stores the *last* session created in $sessions,
# !! because the assignment is performed in *each iteration*.
foreach($vm in $vms){
  $sessions = New-PSSession -ComputerName $vm -Credential $cred
}

直接的解決方法是將賦值移出循環:

# OK - captures *all* session objects created in $sessions
$sessions = foreach($vm in $vms){
  New-PSSession -ComputerName $vm -Credential $cred
}

退一步說:

New-PSSession -ComputerNameInvoke-Command -Session接受一計算機名稱/會話,因此不需要循環

  • 多個會話/計算機名稱傳遞給Invoke-Command具有操作並行運行的巨大優勢。

  • 筆記:

    • Invoke-Command具有內置的節流功能,可以避免同時針對太多機器。 它默認為 32,但可以使用-ThrottleLimit參數進行修改。
    • 來自目標計算機的 Output 將以不可預測的順序到達,但 output 對象裝飾有(除其他外)反映原始計算機的.PSComputerName屬性 - 請參閱此答案的底部部分。

也就是說,您的代碼可以簡化為:

$cred = Get-Credential
$vms = Get-Content C:\Scripts\Tools\vms.txt

$sessions = New-PSSession -ComputerName $vms -Credential $cred

Invoke-Command -Session $sessions -ScriptBlock {
  c:\users\jsmith\documents\VMware-tools-10.3.5.exe /v "/qn REBOOT=R Remove=AppDefense,VMCI”
}

重要

  • 會話最終應在不再需要時使用Remove-PSSession進行清理。
  • 但是,這會停止在這些會話中運行的所有命令,因此如果您通過Invoke-Command調用啟動了異步操作,則需要確保這些操作已先完成 - 請參閱有關VMware-tools-10.3.5.exe的潛在異步執行的評論 -下面的VMware-tools-10.3.5.exe應用程序。

或者,更簡單的是,如果您只需要在每台機器上執行一個命令,在這種情況下無需顯式創建會話,將所有計算機名稱直接傳遞給Invoke-Command-ComputerName參數:

$cred = Get-Credential
$vms = Get-Content C:\Scripts\Tools\vms.txt

# Note the use of -ComputerName
Invoke-Command -ComputerName $vms -Credential $cred -ScriptBlock {
  # Note the use of | Write-Output to ensure synchronous execution.
  c:\users\jsmith\documents\VMware-tools-10.3.5.exe /v "/qn REBOOT=R Remove=AppDefense,VMCI” | Write-Output
}

重要

  • 如果您的應用程序 ( VMware-tools-10.3.5.exe )異步運行,您必須確保其同步執行,否則它可能無法運行完成,因為當腳本塊從給定計算機返回時,隱式創建的遠程 session 將被丟棄。

  • 確保同步執行任何外部(GUI 子系統)可執行文件的一個簡單技巧是 pipe 到Write-Output ,如上所示(或Wait-Process ,如果它不產生控制台輸出) - 請參閱此答案以獲取解釋.

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM