我正在嘗試更改我的類庫以與Mercurial命令行客戶端通信,而1.9客戶端中的新增功能是啓動服務器並通過標準輸入/輸出管道與其通信。這是非常有前途的,因爲使用Mercurial命令行客戶端的主要問題之一是,因爲它是用Python編寫的,所以在客戶端上花費一些開銷,即使只是要求它的版本。獲取.NET Process對象以連續刷新輸入流?
但是,有一個問題。到目前爲止,我已經通過讀取標準輸出/錯誤來從命令行客戶端獲取輸出,並且當進程退出時,流將刷新,並且我可以讀取流結束。
但是,在這種新模式下,進程會將大量文本轉儲到標準錯誤/輸出中,然後等待下一個命令。非常適合減少開銷,但由於.NET緩衝了這些流,所以很糟糕。
換句話說,因爲過程不退出,我不明白的是輸出的,直到最後一個部分:
- 請問進程退出
- 我發出另一個命令
有沒有辦法讓我
- 問緩衝刷新,這意味着我得到無論是在緩衝區,EV如果它不足以使緩衝區自行刷新?
- 如果不是,我可以設置緩衝區大小爲1個字符嗎?
- 我還能做什麼?
如果這是需要的,我可以處理P/Invoke。
這裏有一個LINQPad驗證的概念方案,將說明:
它是什麼旋轉了一個命令提示符,然後餵給它的DIR命令,但是請注意,直到這10秒內環路經過程序是否輸出在生成目錄列表後立即輸出命令提示符的「C:>」提示符。
換句話說,這是命令提示符的作用:
- 農產品目錄列表
- 向另一個命令通過提示 「C:> \」
然而,這是什麼下面的程序看:
- 農產品目錄列表
- (等待10秒)
- 關閉輸入流
看到提示
無效的主要() { 串clientExecutablePath =「CMD。exe文件「;
var psi = new ProcessStartInfo(); psi.FileName = clientExecutablePath; psi.RedirectStandardError = true; psi.RedirectStandardInput = true; psi.RedirectStandardOutput = true; psi.CreateNoWindow = true; psi.WorkingDirectory = @"C:\"; psi.WindowStyle = ProcessWindowStyle.Hidden; psi.UseShellExecute = false; psi.ErrorDialog = false; psi.StandardErrorEncoding = Encoding.GetEncoding("Windows-1252"); psi.StandardOutputEncoding = Encoding.GetEncoding("Windows-1252"); var p = Process.Start(psi); var input = p.StandardInput; var output = p.StandardOutput; var error = p.StandardError; Action<StreamReader, string> reader = delegate(StreamReader streamReader, string prefix) { string line; while ((line = streamReader.ReadLine()) != null) { Debug.WriteLine(prefix + line); } }; IAsyncResult outputReader = reader.BeginInvoke(output, "o: ", null, null); IAsyncResult errorReader = reader.BeginInvoke(error, "e: ", null, null); input.Write("dir\n"); input.Flush(); while (!p.HasExited) { Thread.Sleep(10000); input.Close(); } reader.EndInvoke(outputReader); reader.EndInvoke(errorReader);
}
我改變了計劃砸水銀的依賴,現在它使用常規的CMD.EXE程序來說明。 –
嗨,我在這裏遇到同樣的問題,你是否設法完成它?如果是這樣,怎麼樣? :) – FrieK