显示某个对象的事件历史记录

时间:2014-03-30 12:10:04

标签: c# .net events

想象一下,我有Class1 obj1 = new Class1()。 Class1有许多不同的事件。我想知道什么事件以及什么时候发生,但我不想为这个对象的每个事件创建事件处理程序。我该怎么办?

我想看到的示例输出:

13:04:29 Obj1.OnEvent1
13:04:31 Obj1.OnEvent2
13:04:32 Obj1.OnEvent3
13:04:35 Obj1.OnEvent2
......................

P.S。:我正在使用Visual Studio 2012 Ultimate。

2 个答案:

答案 0 :(得分:1)

您必须使用例如Semantic Logging Application Block

来检测代码

如果您按照惯例使用protected virtual OnEvent方法触发*Event*事件,您会发现实际事件是OnEvent方法实际上是真实事件,而*Event* .NET事件只是其他人可以订阅的通知。并且您希望记录事件而不是事件订阅。

您可以订阅某些内容并对其进行记录,但您很快就会发现您需要记录的事件多于这些事件。

答案 1 :(得分:0)

如果您的eventhandler的委托类型是统一的,您可以迭代从该类型获得的事件并将您的日志记录逻辑附加到该事件。我使用带有Subscibe和Unsubscribe方法的logger类(这里没有实现)

日志

public class EventLogger
{   
    public void Subscribe<T>(T obj)
    {
        // get the type to iterate over the EventInfo's
        var type = typeof (T);
        foreach (var eve in type.GetEvents())
        {
            EventInfo info = eve;
            // attach our logging logic 
            eve.AddEventHandler(obj, 
                new EventHandler((sender, args) =>
                    {
                        Console.WriteLine(
                            "{0} {1}.{2}", 
                            DateTime.Now, 
                            obj,
                            info.Name);
                    }));
        }
    }

    public void Unsubscribe()
    {
        //todo unsubscribe
    }

}

演示类

public class Class1
{
    // public delegate void MyDelegate(string key, DateTime date, int value);

    public event EventHandler Foo;
    public event EventHandler Bar;
    // public event MyDelegate Cancel;

    public void Raise()
    {
        this.Bar(null, EventArgs.Empty);
        // this.Cancel(null, DateTime.Now, 4);
    }
}

用法

var c = new Class1();
c.Bar += (sender, eventArgs) => { Console.WriteLine("bar"); };

// have our logger ready
var logger = new EventLogger();
// attach logging to a specific instance
logger.Subscribe(c);

// raise our events
c.Raise();

请注意,我们只能处理EventHandler类型的委托。 (我评论了代理MyDelegate,因为这会打破这个简单的实现)。如果您有使用不同委托的事件,您需要在Subscribe方法中构建一个switch语句来处理每个不同类型或实现一个方法来生成一个动态程序集,该程序集可以处理如图所示的委托here