Compartir vía


ProcessStartInfo.RedirectStandardError Propiedad

Definición

Obtiene o establece un valor que indica si la salida de errores de una aplicación se escribe en la secuencia de StandardError.

public:
 property bool RedirectStandardError { bool get(); void set(bool value); };
public bool RedirectStandardError { get; set; }
member this.RedirectStandardError : bool with get, set
Public Property RedirectStandardError As Boolean

Valor de propiedad

true si la salida de error se debe escribir en StandardError; si no, false. De manera predeterminada, es false.

Ejemplos

En el ejemplo siguiente se usa el comando junto con un argumento proporcionado por el net use usuario para asignar un recurso de red. A continuación, lee el flujo de error estándar del comando net y lo escribe en la consola.

Process^ myProcess = gcnew Process;
ProcessStartInfo^ myProcessStartInfo = gcnew ProcessStartInfo( "net ",String::Concat( "use ", args[ 0 ] ) );

myProcessStartInfo->UseShellExecute = false;
myProcessStartInfo->RedirectStandardError = true;
myProcess->StartInfo = myProcessStartInfo;
myProcess->Start();

StreamReader^ myStreamReader = myProcess->StandardError;
// Read the standard error of net.exe and write it on to console.
Console::WriteLine( myStreamReader->ReadLine() );
myProcess->Close();
using (Process myProcess = new Process())
{
    ProcessStartInfo myProcessStartInfo = new ProcessStartInfo("net ", "use " + args[0]);

    myProcessStartInfo.UseShellExecute = false;
    myProcessStartInfo.RedirectStandardError = true;
    myProcess.StartInfo = myProcessStartInfo;
    myProcess.Start();

    StreamReader myStreamReader = myProcess.StandardError;
    // Read the standard error of net.exe and write it on to console.
    Console.WriteLine(myStreamReader.ReadLine());
}
Using myProcess As New Process()
    Dim myProcessStartInfo As New ProcessStartInfo("net ", "use " + args(0))

    myProcessStartInfo.UseShellExecute = False
    myProcessStartInfo.RedirectStandardError = True
    myProcess.StartInfo = myProcessStartInfo
    myProcess.Start()

    Dim myStreamReader As StreamReader = myProcess.StandardError
    ' Read the standard error of net.exe and write it on to console.
    Console.WriteLine(myStreamReader.ReadLine())
End Using

Comentarios

Cuando un Process objeto escribe texto en su flujo de error estándar, ese texto se muestra normalmente en la consola. Al redirigir la StandardError secuencia, puede manipular o suprimir la salida de error de un proceso. Por ejemplo, puede filtrar el texto, formatearlo de forma diferente o escribir la salida en la consola y en un archivo de registro designado.

Nota

Debe establecer UseShellExecutefalse en si desea establecer en RedirectStandardErrortrue. De lo contrario, la lectura de la StandardError secuencia produce una excepción.

La secuencia redirigida StandardError se puede leer de forma sincrónica o asincrónica. Métodos como Ready ReadLineReadToEnd realizan operaciones de lectura sincrónicas en el flujo de salida de error del proceso. Estas operaciones de lectura sincrónicas no se completan hasta que las escrituras asociadas Process a su StandardError secuencia o cierran la secuencia.

En cambio, BeginErrorReadLine inicia operaciones de lectura asincrónicas en la StandardError secuencia. Este método habilita un controlador de eventos designado para la salida del flujo y vuelve inmediatamente al autor de la llamada, que puede realizar otro trabajo mientras la salida del flujo se dirige al controlador de eventos.

Nota

La aplicación que procesa la salida asincrónica debe llamar al Process.WaitForExit método para asegurarse de que se ha vaciado el búfer de salida.

Las operaciones de lectura sincrónicas presentan una dependencia entre la lectura del autor de la llamada desde la StandardError secuencia y el proceso secundario que escribe en esa secuencia. Estas dependencias pueden causar condiciones de interbloqueo. Cuando el autor de la llamada lee desde la secuencia redirigida de un proceso secundario, depende del elemento secundario. El autor de la llamada espera a la operación de lectura hasta que el elemento secundario escribe en la secuencia o cierra la secuencia. Cuando el proceso secundario escribe suficientes datos para rellenar su flujo redirigido, depende del elemento primario. El proceso secundario espera a la siguiente operación de escritura hasta que el elemento primario lee de la secuencia completa o cierra la secuencia. La condición de interbloqueo se produce cuando el llamador y el proceso secundario esperan entre sí para completar una operación y ninguno puede continuar. Puede evitar interbloqueos mediante la evaluación de dependencias entre el autor de la llamada y el proceso secundario.

Los dos últimos ejemplos de esta sección usan el Start método para iniciar un archivo ejecutable denominado Write500Lines.exe. El ejemplo siguiente contiene su código fuente.

using System;
using System.IO;

public class Example3
{
   public static void Main()
   {
      for (int ctr = 0; ctr < 500; ctr++)
         Console.WriteLine($"Line {ctr + 1} of 500 written: {ctr + 1/500.0:P2}");

      Console.Error.WriteLine("\nSuccessfully wrote 500 lines.\n");
   }
}
// The example displays the following output:
//      The last 50 characters in the output stream are:
//      ' 49,800.20%
//      Line 500 of 500 written: 49,900.20%
//'
//
//      Error stream: Successfully wrote 500 lines.
Imports System.IO

Public Module Example
   Public Sub Main()
      For ctr As Integer = 0 To 499
         Console.WriteLine($"Line {ctr + 1} of 500 written: {ctr + 1/500.0:P2}")
      Next

      Console.Error.WriteLine($"{vbCrLf}Successfully wrote 500 lines.{vbCrLf}")
   End Sub
End Module
' The example displays the following output:
'      The last 50 characters in the output stream are:
'      ' 49,800.20%
'      Line 500 of 500 written: 49,900.20%
'
'
'      Error stream: Successfully wrote 500 lines.

En el ejemplo siguiente se muestra cómo leer desde un flujo de error redirigido y esperar a que se cierre el proceso secundario. Evita una condición de interbloqueo llamando a p.StandardError.ReadToEnd antes p.WaitForExitde . Una condición de interbloqueo puede dar lugar si el proceso primario llama p.WaitForExit antes p.StandardError.ReadToEnd y el proceso secundario escribe suficiente texto para rellenar la secuencia redirigida. El proceso primario esperaría indefinidamente para que se cierre el proceso secundario. El proceso secundario esperaría indefinidamente para que el elemento primario lea de la secuencia completa StandardError .

using System;
using System.Diagnostics;

public class Example
{
   public static void Main()
   {
      var p = new Process();  
      p.StartInfo.UseShellExecute = false;  
      p.StartInfo.RedirectStandardError = true;  
      p.StartInfo.FileName = "Write500Lines.exe";  
      p.Start();  

      // To avoid deadlocks, always read the output stream first and then wait.  
      string output = p.StandardError.ReadToEnd();  
      p.WaitForExit();

      Console.WriteLine($"\nError stream: {output}");
   }
}
// The end of the output produced by the example includes the following:
//      Error stream:
//      Successfully wrote 500 lines.
Imports System.Diagnostics

Public Module Example
    Public Sub Main()
        Dim p As New Process()
        p.StartInfo.UseShellExecute = False  
        p.StartInfo.RedirectStandardError = True  
        p.StartInfo.FileName = "Write500Lines.exe"  
        p.Start() 

        ' To avoid deadlocks, always read the output stream first and then wait.  
        Dim output As String = p.StandardError.ReadToEnd()  
        p.WaitForExit()

        Console.WriteLine($"{vbCrLf}Error stream: {output}")
    End Sub
End Module
' The end of the output produced by the example includes the following:
'      Error stream:
'      Successfully wrote 500 lines.

Hay un problema similar al leer todo el texto de los flujos de error estándar y de salida estándar. El código de C# siguiente, por ejemplo, realiza una operación de lectura en ambos flujos. Evita la condición de interbloqueo realizando operaciones de lectura asincrónicas en la StandardError secuencia. Una condición de interbloqueo da como resultado si el proceso primario llama p.StandardOutput.ReadToEnd seguido de p.StandardError.ReadToEnd y el proceso secundario escribe suficiente texto para rellenar su flujo de errores. El proceso primario esperaría indefinidamente para que el proceso secundario cierre su StandardOutput secuencia. El proceso secundario esperaría indefinidamente para que el elemento primario lea de la secuencia completa StandardError .

using System;
using System.Diagnostics;

public class Example
{
   public static void Main()
   {
      var p = new Process();  
      p.StartInfo.UseShellExecute = false;  
      p.StartInfo.RedirectStandardOutput = true;  
      string eOut = null;
      p.StartInfo.RedirectStandardError = true;
      p.ErrorDataReceived += new DataReceivedEventHandler((sender, e) => 
                                 { eOut += e.Data; });
      p.StartInfo.FileName = "Write500Lines.exe";  
      p.Start();  

      // To avoid deadlocks, use an asynchronous read operation on at least one of the streams.  
      p.BeginErrorReadLine();
      string output = p.StandardOutput.ReadToEnd();  
      p.WaitForExit();

      Console.WriteLine($"The last 50 characters in the output stream are:\n'{output.Substring(output.Length - 50)}'");
      Console.WriteLine($"\nError stream: {eOut}");
   }
}
// The example displays the following output:
//      The last 50 characters in the output stream are:
//      ' 49,800.20%
//      Line 500 of 500 written: 49,900.20%
//      '
//
//      Error stream: Successfully wrote 500 lines.
Imports System.Diagnostics

Public Module Example
   Public Sub Main()
      Dim p As New Process()  
      p.StartInfo.UseShellExecute = False  
      p.StartInfo.RedirectStandardOutput = True  
      Dim eOut As String = Nothing
      p.StartInfo.RedirectStandardError = True
      AddHandler p.ErrorDataReceived, Sub(sender, e) eOut += e.Data 
      p.StartInfo.FileName = "Write500Lines.exe"  
      p.Start()  

      ' To avoid deadlocks, use an asynchronous read operation on at least one of the streams.  
      p.BeginErrorReadLine()
      Dim output As String = p.StandardOutput.ReadToEnd()  
      p.WaitForExit()

      Console.WriteLine($"The last 50 characters in the output stream are:{vbCrLf}'{output.Substring(output.Length - 50)}'")
      Console.WriteLine($"{vbCrLf}Error stream: {eOut}")
   End Sub
End Module
' The example displays the following output:
'      The last 50 characters in the output stream are:
'      ' 49,800.20%
'      Line 500 of 500 written: 49,900.20%
'      '
'
'      Error stream: Successfully wrote 500 lines.

Puede usar operaciones de lectura asincrónicas para evitar estas dependencias y su potencial de interbloqueo. Como alternativa, puede evitar la condición de interbloqueo creando dos subprocesos y leyendo la salida de cada secuencia en un subproceso independiente.

Se aplica a

Consulte también