中文字幕av专区_日韩电影在线播放_精品国产精品久久一区免费式_av在线免费观看网站

溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點擊 登錄注冊 即表示同意《億速云用戶服務條款》

PowerShell 多線程的使用

發布時間:2020-04-23 20:03:26 來源:網絡 閱讀:33040 作者:beanxyz 欄目:開發技術

今天一個朋友問我在Powershell里面如何能夠并發的ping上萬臺機器?默認的test-connection 盡管有-computer這個參數,他的方式是按順序的挨個ping,全部跑下來可能有好幾個小時。


比如我需要花18秒的時間才能ping完40臺服務器,如果成千上萬的話就很費時間了。


measure-commnd -expression {
$computers=Get-ADComputer -Filter {operatingsystem -like "*2012*"} 

Test-Connection -ComputerName $computers.name -Count 1

}

PowerShell 多線程的使用



這之前,豆子對多線程的使用僅僅限于了解invoke-command可以同時對30個對象操作,經過一番學習,終于發現還有其他 的高級方式。

PowerShell里面,對于多線程的使用大概是兩大方式。

第一個是創建多個后臺的job。這種方式通過start-job或者 -asjob創建后臺job,然后通過get-job獲取當前的任務,通過receive-job來獲取完成任務的結果,最后還得remove-job來釋放內存。缺點是性能不高,尤其在創建job和退出job的過程中會消耗大量時間和資源。


PowerShell 多線程的使用


第二個方式是創建多個runspace,這個工作原理和invoke-command一樣,每一個遠程的session綁定一個runspace。我們可以創建一個runspace pool,指定在這個資源池里面最多可以同時執行多少個runspace。

比起第一種方式,runspace的性能強悍了太多。下面有人做的對比實驗,可以看見幾乎是幾十倍的性能差距。


http://learn-powershell.net/2012/05/13/using-background-runspaces-instead-of-psjobs-for-better-performance/


現在看看怎么來實現。豆子主要參考了這篇博客的方法和原理,寫了一個簡單的腳本來。 

http://thesurlyadmin.com/2013/02/11/multithreading-powershell-scripts/


思路很簡單,創建runspace pool,指定runspace的數量,然后對要測試的對象集合,對每一個對象都創建一個后臺的runspace job,綁定要執行的腳本,傳入參數,把結果保存在ps對象或者hash表中,最后等待所有job結束,輸出結果。


$Throttle = 20 #threads

#腳本塊,對指定的計算機發送一個ICMP包測試,結果保存在一個對象里面
 
$ScriptBlock = {
   Param (
      [string]$Computer
   )
   $a=test-connection -ComputerName $Computer -Count 1 
   
   $RunResult = New-Object PSObject -Property @{
      IPv4Adress=$a.ipv4address.IPAddressToString
      ComputerName=$Computer
      
   }
   Return $RunResult
}


#創建一個資源池,指定多少個runspace可以同時執行

$RunspacePool = [RunspaceFactory]::CreateRunspacePool(1, $Throttle)
$RunspacePool.Open()
$Jobs = @()
 

#獲取Windows 2012服務器的信息,對每一個服務器單獨創建一個job,該job執行ICMP的測試,并把結果保存在一個PS對象中
 
(get-adcomputer -filter {operatingsystem -like "*2012*"}).name | % {
   
   #Start-Sleep -Seconds 1
   $Job = [powershell]::Create().AddScript($ScriptBlock).AddArgument($_)
   $Job.RunspacePool = $RunspacePool
   $Jobs += New-Object PSObject -Property @{
      Server = $_
      Pipe = $Job
      Result = $Job.BeginInvoke()
   }
}
 

 #循環輸出等待的信息.... 直到所有的job都完成 
 
Write-Host "Waiting.." -NoNewline
Do {
   Write-Host "." -NoNewline
   Start-Sleep -Seconds 1
} While ( $Jobs.Result.IsCompleted -contains $false)
Write-Host "All jobs completed!"


#輸出結果 
$Results = @()
ForEach ($Job in $Jobs)
{   $Results += $Job.Pipe.EndInvoke($Job.Result)
}
 
$Results

大概5秒之后 結果就出來了。 如果有興趣的話可以使用measure-command命令來測試不同線程數的效果,根據我的測試,30個進程同時執行只需4秒出結果,而2個同時執行大概需要9秒才能出結果。


PowerShell 多線程的使用


知道原理之后就可以進一步優化和抽象化腳本。這一點已經有人做好了。https://github.com/RamblingCookieMonster/Invoke-Parallel/blob/master/Invoke-Parallel/Invoke-Parallel.ps1


下載,Unlock和dot source之后就能直接調用了。這里提供了一些例子作為參考https://github.com/RamblingCookieMonster/Invoke-Parallel


依葫蘆畫瓢,我想通過他來調用test-connection也是成功的

get-adcomputer -Filter {operatingsystem -like "*2012*"} | select -ExpandProperty name | Invoke-Parallel -ScriptBlock {Test-Connection -computername $_ -count 1}


PowerShell 多線程的使用


再比如我ping 一個IP范圍的計算機

1..254| Invoke-Parallel -ScriptBlock {Test-Connection -ComputerName "10.2.100.$_" -Count 1 -ErrorAction SilentlyContinue -ErrorVariable err | select Ipv4address, @{n='DNS';e={[System.Net.Dns]::gethostentry($_.ipv4address).hostname}}} -Throttle 20


PowerShell 多線程的使用


最后,網上也有現成的腳本用來并發的測試ping,原理也是調用上面的invoke-parallel函數,不過他還增加了其他的函數用來測試rdp,winrm,rpc等遠程訪問的端口是否打開,進一步擴充了功能。可以直接在這里下載

http://ramblingcookiemonster.github.io/Invoke-Ping/

invoke-ping -ComputerName (Get-ADComputer -Filter {operatingsystem -like "*2012*"}).name -Detail RDP,rpc | ft -Wrap

PowerShell 多線程的使用


參考資料:

1. http://learn-powershell.net/2012/05/13/using-background-runspaces-instead-of-psjobs-for-better-performance/

2. https://github.com/RamblingCookieMonster/Invoke-Parallel

3. http://thesurlyadmin.com/2013/02/11/multithreading-powershell-scripts/

4. http://ramblingcookiemonster.github.io/Invoke-Ping/

5. http://learn-powershell.net/2012/05/10/speedy-network-information-query-using-powershell/



向AI問一下細節

免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。

AI

阿尔山市| 图们市| 青河县| 黄石市| 中牟县| 子长县| 信阳市| 尼勒克县| 福清市| 盐源县| 军事| 仙游县| 余江县| 永州市| 平南县| 蒲江县| 红安县| 滨州市| 安阳市| 扬州市| 绥化市| 东光县| 邯郸县| 外汇| 苍梧县| 三门峡市| 凤阳县| 翼城县| 酒泉市| 德兴市| 大城县| 湛江市| 富阳市| 南丹县| 成安县| 东平县| 永德县| 五常市| 绥宁县| 临高县| 精河县|