Si necesitamos que nuestra aplicación en .NET escriba en un fichero Log, ¿para qué inventar la rueda? podemos hacer uso de las clases estáticas Trace y Debug del espacio de nombres System.Diagnostics. La primera clase generará salida sólo si compilamos la aplicación en modo Debug.

Estas dos clases comparten uno o varios listeners (agentes de escucha) por donde se escribirá la salida:

  • TextWriterTraceListener para escribir en un fichero físico.
  • EventLogTraceListener para escribir en el visor de eventos.
  • ConsoleTraceListener para escribir en la consola.

Por defecto Debug y Trace tienen un DefaultTraceListener.

DefaultTraceListener se puede eliminar con el elemento <clear>o <remove> en el fichero de configuración o llamando al método Clear en la propiedad Listeners de la clase Debug o Trace.

Los métodos mas importantes de Debug y Trace son:

  • WriteLine para escribir una linea de mensaje en los listeners.
  • WriteLineIf para escribir una linea de mensaje en los listeners si se cumple la condición.
  • Indent para añadir una sangria a la salida.
  • Unindent para eliminar una sangria.
  • Assert para comprobar una condición; si esta es false, muestra un cuadro de mensaje con la pila de llamadas.
  • Flush para vacíar el búfer.

Ejemplo 1. Por defecto DefaultTraceListener escribe en la ventana de resultados.

Debug.WriteLine("Esto es un mensaje en debug");
Trace.WriteLine("Esto es un mensaje en trace");
Debug.Flush();
Trace.Flush();

Si compilamos el ejemplo 1 como Release comprobaremos que no se produce la salida de Debug:

escribir facilmente un fichero Log en .NET Framework

Ejemplo 2. Anulación de DefaultTraceListener y redirección de la salida a la consola y a un fichero Log.

Debug.Listeners.Remove("Default");
TextWriterTraceListener logFile = new TextWriterTraceListener("c:/MiFicheroLog.log");
Trace.Listeners.Add(logFile);
ConsoleTraceListener logConsole = new ConsoleTraceListener();
Trace.Listeners.Add(logConsole);
Debug.WriteLine("Esto es un mensaje en debug");
Trace.WriteLine("Esto es un mensaje en trace");
Debug.Flush();
Trace.Flush();

Ejemplo 3. Una buena idea es hacer uso de la clase System.Diagnostics.Stopwatch cuando necesitamos dejar constancia en un Log de la duración de un proceso.

Trace.WriteLine("Inicio del proceso");
Stopwatch sw = Stopwatch.StartNew();
MiProceso();
sw.Stop();
Trace.WriteLine("Duración del proceso: " + sw.Elapsed.ToString());

Tambien se puede añadir o eliminar TraceListeners mediante el .config de la aplicación. De este modo no es necesario recompilar la aplicación.

Ejemplo 4. Anulación de DefaultTraceListener y redirección de la salida a un fichero Log.

<?xml version="1.0" encoding="utf-8" ?>
<configuration>
  <system.diagnostics>
    <trace autoflush="false" indentsize="4">
      <listeners>
        <remove name="Default" />
        <add name="myListener"  type="System.Diagnostics.TextWriterTraceListener" initializeData="c:/MiFicheroLog.log" />
      </listeners>
    </trace>
  </system.diagnostics>
</configuration>

Referencias:
DefaultTraceListener (Clase)
[VS2010] “Hola Mundo” con Moles