【问题标题】:stderr in the shell and a copy into log fileshell 中的 stderr 并复制到日志文件中
【发布时间】:2012-11-25 13:26:41
【问题描述】:

我使用 Process 类在我的 WPF C# 应用程序中运行 pscp.exe(来自 Putty),如下所示:

Process p = new Process();
p.StartInfo.FileName = "pscp.exe";
p.StartInfo.Arguments = "-v -scp -pw xx toto@192.168.0.1:/path .";
p.Start();
p.WaitForExit();

进程打开命令提示符并正确退出,就ok了。

现在,我想登录一个文件stderr的进程,没问题,我用:

p.StartInfo.UseShellExecute = false;
p.StartInfo.RedirectStandardError = true;

然后我在我的文件中打印流,但 shell 中没有显示任何内容(没关系,这是一个重定向)。

我的需要是在 shell 中显示标准错误并将其复制到我的日志文件中(没有重定向,我想要两次)。

编辑:一个代表我需要的明确示例: 想象一个 WPF 应用程序,它有一个调用此函数的按钮:

Process p = new Process();
p.StartInfo.FileName = "pscp.exe";
p.StartInfo.Arguments = "-v -scp -pw xx toto@192.168.0.1:/path .";
p.Start();
p.WaitForExit();

进程以 cmd 提示符开始(在其中打印 stdout + stderr),同时在日志文件中打印 stderr。

有什么想法吗?

【问题讨论】:

  • 是的,我有办法做到这一点。我忘了说我的应用程序不是控制台应用程序,而是 WPF 应用程序。所以,Console.WriteLine() 不适应,是吗?
  • 是的,那完全是另一回事。 Log4Net 允许您同时登录到文件 控制台,您可能想检查一下。我正在删除我之前的(现在没有实际意义的)评论。
  • 谢谢,非常好的工具,这可以帮助我进行其他开发,但很抱歉我不明白 Log4Net 如何解决我的问题。如何在不使用禁用我的提示的UseShellExecute = false; 的情况下重定向标准错误(RedirectStandardError = true;)?
  • 对不起,我把它弄反了。如果我能让它工作,我会摆弄一些代码并回复答案。
  • 上,你成功了吗?

标签: c# wpf process stderr


【解决方案1】:

如 Hylaean 所述:首先,您准备 Process 对象并注册事件:

p.StartInfo.UseShellExecute = false;
p.StartInfo.RedirectStandardOutput = true;
p.StartInfo.RedirectStandardError = true;
p.StartInfo.CreateNoWindow = true;
p.ErrorDataReceived += new DataReceivedEventHandler(shell_ErrorDataReceived);
p.OutputDataReceived += new DataReceivedEventHandler(shell_OutputDataReceived);

shellOut = openWriter(outputFileName);   //  opens a StreamWriter

在事件处理程序中,您可以对 stderr 和 stdout 数据做您喜欢的事情:

// write out info to the display window
private static void shell_OutputDataReceived(object sender, DataReceivedEventArgs e)
{
    string s = e.Data;

    if ((s != null) && (shellOut != null))
    {
        SomeOutOrLog(s);         //  output or log the string to somewhere
        shellOut.WriteLine(s);
    }
}

private static void shell_ErrorDataReceived(object sender, DataReceivedEventArgs e)
{
    string s = e.Data;

    if (s != null) 
    {
        SomeOutOrLog(s);   //  output or log the string to somewhere
    }
}

【讨论】:

    【解决方案2】:

    您需要订阅 ErrorDataReceivedEvent

    http://msdn.microsoft.com/en-us/library/system.diagnostics.process.errordatareceived.aspx

    Process p = new Process();
    p.StartInfo.FileName = "pscp.exe";
    p.StartInfo.Arguments = "-v -scp -pw xx toto@192.168.0.1:/path .";
    p.StartInfo.UseShellExecute = false;
    p.StartInfo.RedirectStandardError = true;
    p.ErrorDataReceived += (o, e) => Console.Error.WriteLine(e.Data);
    p.Start();
    p.WaitForExit();
    

    【讨论】:

    • 这个不能解决我的问题,需要看cmd提示。要订阅事件,RedirectStandardError 必须为 True。所以这是一个重定向而不是标准错误的副本。
    • 您可以做很多事情,而不仅仅是记录,写入 sdterr(显示在代码中)并写入您的日志文件。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2012-11-01
    • 1970-01-01
    • 2015-06-26
    • 2022-12-07
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多