通过事件实现简单的进程内业务实体监控
(转载请注明出处)
虽然委托结构灵活,而且其方法签名可以适配的参数数量和类型更为丰富,但为了和其他第三方软件、系统集成方面,工程中我们也许用到事件(Event)的机会更多。事件是委托的特例,“特”在如下4方面:
- 返回值为void
- 第一个参数sender是System.Object
- 第二个参数继承自EventArgs或其子类
- 仅限俩参数
就像事物的两面一样,事件约束较多对我们自己是这样对其他开发者也是这样,所以在项目集成过程中,定义过于复杂的委托反而可能成为双方的断层,还需额外的适配器或观察者解决问题,相对而言基于事件进行异步通知集成更容易实现。下面我们看一个模拟的监控程序:
需求是这样的,我们需要对订单的新增和修改进行记录,新增相对好说,他的入口API固定,但订单的字段比较多,涉及的业务流程也复杂,修改API比较分散。我们的监控程序只需要知道新增多少条,总共进行过多少次修改,这时应用层通过事件监控不失为一个方法。
C#
业务实体和事件监控器
using System;
namespace MarvellousWorks.PracticalPattern.Concept.Delegating
{
/// business entity public class Order
{
public void Create() { EventMonitor.Added(this, null); }
public void ChangeDate() { EventMonitor.Modified(this, null); }
public void ChangeOwner() { EventMonitor.Modified(this, null); }
public void ChangeID() { } // do nothing } /// event monitor public static class EventMonitor
{
public static EventHandler<EventArgs> Modified;
public static EventHandler<EventArgs> Added;
static EventMonitor()
{
Modified = OnModified;
Added = OnAdded;
}
public static int ModifiedTimes
{
get;
private set;
}
public static int AddedTimes
{
get;
private set;
}
static void OnModified(object sender, EventArgs args) { ModifiedTimes++; }
static void OnAdded(object sender, EventArgs args) { AddedTimes++; }
}
}
C# Unit Test
[TestMethod]
public void EventMonitorSimulate()
{
Order order1 = new Order();
order1.Create(); // add 1 order1.ChangeDate(); // modify 1 order1.ChangeDate(); // modify 2 order1.ChangeOwner(); // modify 3 Order order2 = new Order();
order2.Create(); // add 2 order2.ChangeOwner(); // modify 4 order2.ChangeID(); // modify still 4 Assert.AreEqual<int>(2, EventMonitor.AddedTimes);
Assert.AreEqual<int>(4, EventMonitor.ModifiedTimes);
}
单元测试结果表明采用事件监控的可行性:
- 分散的业务实体对象其监控信息可以集中反映在同一个监控器中
- 监控器可凭借事件委托方式更新计数
贸易电子化,技术全球化