Java 中的事件聚合器模式:集中大型应用程序中的事件管理
大约 3 分钟
也称为
- 事件通道
- 事件中心
- 消息中心
事件聚合器设计模式的意图
事件聚合器是一种用于处理系统中事件的设计模式。它集中了事件处理逻辑,使事件管理和维护更加容易。事件聚合器设计模式旨在将事件生成与事件处理解耦。这种设计模式收集来自多个来源的事件,并将它们路由到相应的处理程序。
事件聚合器模式的详细解释以及现实世界示例
现实世界示例
事件聚合器模式通常比作车轮中的轮毂。在这个比喻中,事件聚合器是轮毂,而辐条是事件源。轮毂从所有辐条收集事件,然后将它们分发到相应的处理程序。
通俗易懂地讲
事件聚合器是一种设计模式,它允许多个事件源通过一个中心点与事件处理程序通信,而不是让每个事件源直接与每个处理程序通信。
Java 中事件聚合器模式的编程示例
考虑以下示例,其中我们使用事件聚合器来处理多个事件。
乔弗里国王坐在铁王座上,统治着维斯特洛的七大王国。他从国王之手(他的二把手)那里获得大部分重要信息。国王之手也有许多亲密的顾问,他们向他提供有关王国中发生的事件的相关信息。
在我们的编程示例中,我们展示了事件聚合器模式的实现。有些对象是事件监听器,有些是事件发射器,而事件聚合器同时兼具两者。
public interface EventObserver {
void onEvent(Event e);
}
public abstract class EventEmitter {
private final Map<Event, List<EventObserver>> observerLists;
public EventEmitter() {
observerLists = new HashMap<>();
}
public final void registerObserver(EventObserver obs, Event e) {
// implementation omitted
}
protected void notifyObservers(Event e) {
// implementation omitted
}
}
乔弗里国王
正在监听来自 国王之手
的事件。
@Slf4j
public class KingJoffrey implements EventObserver {
@Override
public void onEvent(Event e) {
LOGGER.info("Received event from the King's Hand: {}", e.toString());
}
}
国王之手
正在监听来自他的下属 小指头
、瓦里斯
和 侦察员
的事件。他从他们那里听到的一切,都会传递给 乔弗里国王
。
public class KingsHand extends EventEmitter implements EventObserver {
public KingsHand() {
}
public KingsHand(EventObserver obs, Event e) {
super(obs, e);
}
@Override
public void onEvent(Event e) {
notifyObservers(e);
}
}
例如,瓦里斯
每个星期天都会发现一个叛徒,并通知 国王之手
。
@Slf4j
public class LordVarys extends EventEmitter implements EventObserver {
@Override
public void timePasses(Weekday day) {
if (day == Weekday.SATURDAY) {
notifyObservers(Event.TRAITOR_DETECTED);
}
}
}
以下代码片段演示了如何构建和连接这些对象。
public static void main(String[] args) {
var kingJoffrey = new KingJoffrey();
var kingsHand = new KingsHand();
kingsHand.registerObserver(kingJoffrey, Event.TRAITOR_DETECTED);
kingsHand.registerObserver(kingJoffrey, Event.STARK_SIGHTED);
kingsHand.registerObserver(kingJoffrey, Event.WARSHIPS_APPROACHING);
kingsHand.registerObserver(kingJoffrey, Event.WHITE_WALKERS_SIGHTED);
var varys = new LordVarys();
varys.registerObserver(kingsHand, Event.TRAITOR_DETECTED);
varys.registerObserver(kingsHand, Event.WHITE_WALKERS_SIGHTED);
var scout = new Scout();
scout.registerObserver(kingsHand, Event.WARSHIPS_APPROACHING);
scout.registerObserver(varys, Event.WHITE_WALKERS_SIGHTED);
var baelish = new LordBaelish(kingsHand, Event.STARK_SIGHTED);
var emitters = List.of(
kingsHand,
baelish,
varys,
scout
);
Arrays.stream(Weekday.values())
.<Consumer<? super EventEmitter>>map(day -> emitter -> emitter.timePasses(day))
.forEachOrdered(emitters::forEach);
}
运行示例后的控制台输出。
21:37:38.737 [main] INFO com.iluwatar.event.aggregator.KingJoffrey -- Received event from the King's Hand: Warships approaching
21:37:38.739 [main] INFO com.iluwatar.event.aggregator.KingJoffrey -- Received event from the King's Hand: White walkers sighted
21:37:38.739 [main] INFO com.iluwatar.event.aggregator.KingJoffrey -- Received event from the King's Hand: Stark sighted
21:37:38.739 [main] INFO com.iluwatar.event.aggregator.KingJoffrey -- Received event from the King's Hand: Traitor detected
事件聚合器模式的详细解释以及现实世界示例

何时在 Java 中使用事件聚合器模式
在以下情况下使用事件聚合器模式
- 您有多个事件源和处理程序。
- 您希望解耦事件生成和处理逻辑。
- 您需要一个集中的事件管理系统。
Java 中事件聚合器模式的现实世界应用
- 企业应用程序集成,其中系统需要一个中心点来处理由各种子系统生成的事件。
- 复杂的 GUI 应用程序,其中界面中一个部分的用户操作需要影响其他部分,而无需在组件之间进行紧密耦合。
事件聚合器模式的优缺点
优点
- 解耦:通过集中事件处理,事件聚合器最大限度地减少了组件之间的直接交互,从而创建了一个更模块化、更容易管理的系统。
- 提高灵活性和可扩展性:添加新的发布者或订阅者所需的努力更少,因为中央聚合器处理所有路由。
- 简化组件接口:组件只需要知道事件聚合器,而不需要知道其他组件。
- 集中事件管理:使系统更容易维护。
权衡取舍
- 聚合器的复杂性:如果设计不当,事件聚合器本身可能会成为一个复杂且维护成本高的组件。
- 潜在的性能瓶颈:如果未适当扩展,集中事件处理机制可能会成为系统中的瓶颈。
相关的 Java 设计模式
- 中介者:类似于中介者,它抽象了组件之间的直接通信,但专门针对事件消息。
- 观察者:事件聚合器模式通常使用观察者模式实现,其中聚合器观察事件并通知订阅者。
- 发布/订阅:事件聚合器可以看作是发布/订阅模式的一种特殊情况,聚合器充当代理。