事件机制spring
相关概念: 事件EventObject 事件生成器 事件的产生者,生成事件后,使用事件发布器发布事件。 事件生成器工厂 生产多种类型的事件生成器 事件发布器EventPublisher 发布事件:将事件发布到广播器中。 事件广播器 通知在事件监听器注册表中注册的事件监听器。即将事件dispatch到对应的监听器上。 事件监听器EventListener 监听事件,并作相应的处理。 事件监听器注册表 管理事件监听器,广播器经过注册表来寻找指定的监听器。 执行流程: 1)初始化监听器注册表。 2)businessService ---> 生成事件 ---> 发布事件 ---> 广播器:从注册表中获取指定类型的监听器,并通知监听器 ---> 各个监听器响应该事件。
jdk的事件机制:数据结构
事件:EventObject 未定义事件发布器 事件监听器:EventListener
spring的事件机制:app
事件:ApplicationEvent 继承了jdk的EventObject 事件生成器:spring中并无定义事件生成器,spring直接经过new ApplicationEvent的实现类来生成事件。 事件发布器:ApplicationEventPublisher 实现: ApplicationContext继承了ApplicationEventPublisher,即ApplicationContext的实现类做为不一样的事件发布器。 将事件发布到广播器中:AbstractApplicationContext调用广播器的multicastEvent()方法将事件发布到广播器中。 事件广播器:ApplicationEventMulticaster 实现: 默认广播器:SimpleApplicationEventMulticaster 使用multicastEvent()方法来广播事件: 从注册表中获取监听器:使用getApplicationListeners()方法从注册表中获取事件监听器。 通知监听器:使用invokeListener()方法来通知指定的监听器,invokeListener()方法内调用了监听器的onApplicationEvent方法。 事件监听器:ApplicationListener 继承了jdk的EventListener 事件监听器注册表: 实现: 数据结构:AbstractApplicationContext的applicationListeners属性: private final Set<ApplicationListener<?>> applicationListeners = new LinkedHashSet<ApplicationListener<?>>(); 注册监听器:经过AbstractApplicationContext的addApplicationListener()方法将监听器添加到注册表中。 初始化:容器启动的时候,会初始化注册表。 eg:在建立容器和初始化容器时会调用FrameworkServlet.configureAndRefreshWebApplicationContext()方法,该方法会调用addApplicationListener()方法来注册监听器。 说明: /** * ApplicationContext(更确切的说是AbstractApplicationContext)在spring的事件机制中扮演了多个角色:事件发布器、事件广播器、监听器注册表 */ public abstract class AbstractApplicationContext implements ApplicationContext { // ApplicationContext继承了ApplicationEventPublisher,故AbstractApplicationContext即事件发布器 // 事件广播器 /** Helper class used in event publishing */ private ApplicationEventMulticaster applicationEventMulticaster; // 事件监听器注册表 private final Set<ApplicationListener<?>> applicationListeners = new LinkedHashSet<ApplicationListener<?>>(); /** ApplicationEvents published early */ private Set<ApplicationEvent> earlyApplicationEvents; @Override public void addApplicationListener(ApplicationListener<?> listener) { if (this.applicationEventMulticaster != null) { this.applicationEventMulticaster.addApplicationListener(listener); } else { this.applicationListeners.add(listener); } } // 发布事件 @Override public void publishEvent(ApplicationEvent event) { publishEvent(event, null); } protected void publishEvent(Object event, ResolvableType eventType) { // Decorate event as an ApplicationEvent if necessary ApplicationEvent applicationEvent; if (event instanceof ApplicationEvent) { applicationEvent = (ApplicationEvent) event; } else { applicationEvent = new PayloadApplicationEvent<Object>(this, event); if (eventType == null) { eventType = ((PayloadApplicationEvent)applicationEvent).getResolvableType(); } } // Multicast right now if possible - or lazily once the multicaster is initialized if (this.earlyApplicationEvents != null) { this.earlyApplicationEvents.add(applicationEvent); } else { getApplicationEventMulticaster().multicastEvent(applicationEvent, eventType); } // Publish event via parent context as well... if (this.parent != null) { if (this.parent instanceof AbstractApplicationContext) { ((AbstractApplicationContext) this.parent).publishEvent(event, eventType); } else { this.parent.publishEvent(event); } } } } 举例: duboo服务的导出: 监听器:ServiceBean ServiceBean实现了spring的ApplicationListener接口,而且监听着spring的上下文刷新事件(ContextRefreshedEvent),当监听到spring的上下文刷新事件时,执行服务导出操做。