2016-08-19 61 views
0

我有我認爲是獨特的情況。我有大約15個PowerShell腳本,我想在一系列計算機上運行,​​並讓腳本返回每個主機上每個腳本的輸出。一次在多臺機器上運行PowerShell腳本列表

我有什麼作品,但它沒有出現在每個主機上同時運行腳本,而且速度很慢。任何幫助表示讚賞。

for (int i = 0; i < hosts.Length; i++) 
      { 
       var remoteComputer = new Uri(String.Format("{0}://{1}:5985/wsman", "http", hosts[i])); 
       var connection = new WSManConnectionInfo(remoteComputer); 
       var runspace = RunspaceFactory.CreateRunspace(connection); 
       runspace.Open(); 

       for (int ii = 0; ii < powerShellfiles.ToArray().Length; ii++) 
       { 
        using (PowerShell ps = PowerShell.Create()) 
        { 
         ps.Runspace = runspace; 
         //ps.AddScript(powerShellfiles[ii]); 
         ps.AddScript(powerShellfiles[ii]); 
         IAsyncResult async = ps.BeginInvoke(); 
         List<string> aa = ps.EndInvoke(async).SelectMany(x => x.Properties.Where(y => y.Name == "rec_num").Select(z => z.Value.ToString())).ToList(); 
         keysFromhost.AddRange(aa); 
        } 

       }; 

      }; 

powerShellfiles中的每個項目都是.ps1文件本身的文本。

回答

2

所有你需要做的就是使用Parallel.ForEach異步框架/類和方法。 這是一個非常簡單的解決方案。Parallel將爲您提供的數組中的每個項目生成單獨的線程,並且直到所有線程完成執行後纔會返回,您還可以檢查返回值並查看是否所有任務都已成功完成。

現在你的結果,你需要一個線程安全的集合,這個一直是.NET Framework的一部分,因爲3.0我會用我下面指定的一個:

System.Collections.Generic.SynchronizedCollection<T> 

例子:

 private void RunPowerShell(string[] hosts) 
     { 
      Parallel.ForEach(hosts, (host) => { 
       var remoteComputer = new Uri(String.Format("{0}://{1}:5985/wsman", "http", hosts)); 
       var connection = new WSManConnectionInfo(remoteComputer); 
       var runspace = RunspaceFactory.CreateRunspace(connection); 
       runspace.Open(); 

       for (int ii = 0; ii < powerShellfiles.ToArray().Length; ii++) 
       { 
        using (PowerShell ps = PowerShell.Create()) 
        { 
         ps.Runspace = runspace; 
         //ps.AddScript(powerShellfiles[ii]); 
         ps.AddScript(powerShellfiles[ii]); 
         IAsyncResult async = ps.BeginInvoke(); 
         List<string> aa = ps.EndInvoke(async).SelectMany(x => x.Properties.Where(y => y.Name == "rec_num").Select(z => z.Value.ToString())).ToList(); 
         keysFromhost.AddRange(aa); 
        } 

       }; 
      }); 
     } 
+0

這是有效的,但是對於我添加代碼的每個主機來說,速度慢了20秒。我想讓PowerShell文件在給定的機器上同時被關閉。 –

+0

現在我再次查看您的代碼。 這是一種錯誤,你應該加入一個回調到你的開始調用,然後在回調中你結束調用不會開始調用和結束調用在相同的方法執行。 https://msdn.microsoft.com/en-us/library/dd182439(v=vs.85).aspx – JQluv

相關問題