Можно ли настроить трассировку через TraceSource через код из внешней сборки
Наиболее TraceSource
Примеры трассировки показывают, как это делается с помощью конфигурации. Я пытаюсь добиться этого с помощью кода.
У меня есть простая сборка следующим образом:
using System;
using System.Diagnostics;
using System.Threading;
namespace TracingLib
{
public class AppTracer
{
public event EventHandler AppStarted;
public event EventHandler AppStopped;
private bool CancelRequested = false;
public void Start()
{
Thread thread = new Thread(new ThreadStart(() =>
{
if(AppStarted != null) AppStarted(this, new EventArgs());
TraceSource ts = new TraceSource("ThreadSource");
ts.TraceInformation("Thread Begins");
//ts.Flush();
int i = 0;
while (!CancelRequested)
{
ts.TraceInformation("i: {0}", i++);
//ts.Flush();
Debug.Print("i : {0}", i);
Thread.Sleep(5000);
}
if (AppStopped != null) AppStopped(this, new EventArgs());
}));
thread.Start();
}
public void Stop()
{
CancelRequested = true;
}
}
}
Я потребляю это в консольном приложении.
using System;
using System.Threading;
using TracingLib;
namespace caTracingLibImplementation
{
class Program
{
static void Main(string[] args)
{
AppTracer tracer = new AppTracer();
ManualResetEvent waiter = new ManualResetEvent(false);
tracer.AppStopped += (sender, e) =>
{
waiter.Set();
};
TraceSource ts = new TraceSource("ThreadSource");
ts.Listeners.Add(new ConsoleTraceListener());
var sw = new SourceSwitch("foo");
sw.Level = SourceLevels.Warning;
ts.Switch = sw;
tracer.Start();
Console.WriteLine("AppTracer started...");
Thread.Sleep(10000);
tracer.Stop();
Console.WriteLine("AppTracer stopped...");
Console.WriteLine("Waiting to stop...");
waiter.WaitOne();
Console.WriteLine("End of program");
}
}
}
Если я пытаюсь включить трассировку через консольное приложение, я не вижу сообщений трассировки.
2 ответа
Во-первых, вам необходимо предоставить TraceListeners для TraceSource, определенного в AppTracer.
Этот код будет работать с использованием файлов конфигурации, будет работать, потому что.NET Framework хранит один экземпляр каждого слушателя, полученный из файла конфигурации, и назначает их каждому TraceSource на основе начального строкового параметра.
Если строковый параметр для TraceSource не определен в app.config, то слушатели не будут сохранены в глобальном состоянии. Поэтому каждый экземпляр TraceSource должен иметь всех слушателей, предоставленных ему.
Источник TraceSource.Initialize()
Во-вторых, переключатель: sw.Level = SourceLevels.Warning;
отключит любые операторы, зарегистрированные с: ts.TraceInformation()
Если вы настраиваете свой TraceSource во время выполнения, я думаю, что наиболее подходящим решением для вашего кода является:
- Добавьте этот динамический TraceSource в конструктор AppTracer.
- ИЛИ передать TraceSource через Start().
Я бы склонился к #1 над #2.
Как упоминает пользователь1112560, вы не увидите вывод TraceInformation, если для вашего уровня переключателя установлено предупреждение. Приоритет: Выкл., Ошибка, Предупреждение, Информация, Подробно. Посмотрите Коммутаторы трассировки MSDN.