2016-05-25 26 views
2

我有一個PowerShell腳本,需要調用C#才能工作,其中一些是異步的。在調試僅在從PowerShell調用C#代碼時發生的一些錯誤時,我注意到了一些我並不期待的事情。在C#代碼中,如果我打電話給Console.WriteLine,它會按預期的方式寫入PowerShell控制檯,除非我正在使用PowerShell ISE,並且在異步函數中執行了等待後調用它。當從powershell調用異步C#代碼時無法寫入控制檯ISE

下面是一個示例腳本,顯示問題:

$source = @" 
using System; 
using System.Collections.Generic; 
using System.Linq; 
using System.Threading; 
using System.Threading.Tasks; 

public class TestClass 
{ 
    public static int TestWrapper() 
    { 
     var task = TestAsync(); 
     task.Wait(); 
     return task.Result; 
    } 

    private static async Task<int> TestAsync() 
    { 
     Console.WriteLine("Before await"); 
     await Task.Run(() => { Thread.Sleep(2000); return; }); 
     Console.WriteLine("After await"); 
     return 2; 
    } 
} 

"@ 

Add-Type -TypeDefinition $source 
[TestClass]::TestWrapper() 

在這裏,我打電話是一個異步函數,等待它完成,並返回結果。在函數內部,我只是在返回一個值之前嘗試記錄線程休眠幾秒鐘之前和之後,以便我知道函數完全執行。

我希望看到:

Before await 
After await 
2 

這就是我所看到的C#控制檯應用程序或基本PowerShell中運行時,而是通過PowerShell ISE中運行的時候,我看到:

Before await 
2 

任何人都可以解釋爲什麼會這樣嗎?

+0

當我嘗試它時,它工作正常。 – sstan

+0

你知道嗎,我不認爲powershell和PowerShell ISE會有區別,但我想是有的。 –

+0

啊,是的。運行PowerShell ISE時,我可以重現您的問題。 – sstan

回答

5

PowerShell ISE使用Console.SetOutHostTextWriter在PowerShell ISE主機窗口上捕獲並打印Console.WriteLine輸出。僅當主機註冊(HostTextWriter.RegisterHost)爲當前線程時,HostTextWriter纔會將Console.WriteLine重定向到PowerShell主機。

如果沒有SynchronizationContext繼續引起的await關鍵字將在任意線程池線程中執行,這可能沒有任何已註冊的PowerShell主機將Console.WriteLine重定向到。

相關問題