2

我一直在使用 C#System.Diagnostics.Process来监视命令行实用程序的输出。

我正在“内部”监控的进程会启动第二个进程,一旦启动,我就不会从进程对象收到更多输出。

令人沮丧的是,如果您使用 cmd.exe(手动)执行相同的命令(我使用 System.Diagnostics.Process 对象启动),控制台会输出我需要在 C# 应用程序中看到的每一行!

但是,如果我(出于测试目的)使用 System.Diagnostics.Process 对象启动 cmd.exe 并运行该命令,它仍然会在之前的同一点停止输出(直接启动 process1.exe);此时使用了 second.exe。我认为这个测试会整合所有相关流程的所有输出,但事实并非如此。如何将所有这些输出输入到我的 C# 应用程序中?

4

2 回答 2

5

这样做的原因是它System.Diagnostics.Process实际上只是监视它所连接的进程。

避免此问题的一种方法是让您的第一个应用程序在启动第二个应用程序时输出,并且当接收到该输出时,从您的主应用程序监视以从(现在是第三个)应用程序创建进程。一旦第三个应用程序启动,它应该出现在System.Diagnostics.Process.GetProcesses()数组中,然后您可以附加到它的OutputDataReceived事件。

然后,您的代码将如下所示(未经测试):

private void firstProcess_OutputDataReceived(object sender, System.Diagnostics.DataReceivedEventArgs e)
{
    if (e.Data == "Starting next process")
    {
        System.Diagnostics.Process newProcess = null;

        while (newProcess == null)
        {
            System.Diagnostics.Process[] procs = System.Diagnostics.Process.GetProcesses();

            foreach (System.Diagnostics.Process proc in procs)
            {
                if (proc.ProcessName == "newProcess")
                {
                    newProcess = proc;
                    break;
                }
            }

            System.Threading.Thread.Sleep(100);
        }

        newProcess.OutputDataReceived += new System.Diagnostics.DataReceivedEventHandler(newProcess_OutputDataReceived);
    }
}

void newProcess_OutputDataReceived(object sender, System.Diagnostics.DataReceivedEventArgs e)
{
    // Do something with your data received here.
}

请注意,这只是一个示例,如果您的第三个进程无法启动或结束太快,则此方法将陷入无限循环。这个示例只是为了向您提供知识来构建适用于您的特定情况的东西,我并不完全熟悉。您至少应该确保 while 循环不会永远持续下去,并且您可能还需要进行一些其他调整。

编辑:或者,如果您不能将源代码修改为第一个应用程序,您可以简单地创建一个以这种方式(使用 while 循环)不断监视的新线程,并在单独的类中处理来自第三个进程的输出,或者只需将第三个进程的输出重新路由到第二个进程的输出的处理程序中,这样您就可以使用一个方法来处理两个进程的所有输出。

于 2010-01-18T22:35:44.670 回答
1

你需要启动 cmd.exe 吗?难道你不能直接在你的 Process 中启动 rsync 进程,然后使用类似这个问题中描述的技术来捕获命令执行的输出,以便你可以在你的代码中使用它们?

于 2010-01-18T22:25:04.793 回答