ApplicationContext 扩展了 ApplicationEventPublisher 接口. 让容器拥有了发布应用文上下事件的能力. 包括容器启动事件, 关闭事件的功能.
先解释几个名词:
(1)事件源: 事件的产生者. 任何一个 EventObject 都必须拥有一个事件源.
(2)事件监听器注册表: 组件或框架的时间监听器必须有所依存. 必须提供一个地方保存时间监听器. 这便是事件监听器注册表. 一个事件监听器注册到组件或框架中, 其实就是保存在事件监听器注册表中. 当组件或者框架的事件源产生事件时, 就会通知这些位于事件监听器注册表的监听器.
(3)事件广播器: 是事件和事件监听器沟通的桥梁. 负责把事件通知给事件监听器.
Spring 事件类结构
1.事件类: ApplicatinEvent. 唯一构造函数是 ApplicationEvent(Object source). 通过 source 指定事件源. 有两个子类.
2.事件监听器接口
Spring 所有的事件监听器都继承自 ApplicationListern 接口.
ApplicationListern 接口只定义了一个方法: onApplicationEvent( E event). 该方法接收 ApplicationEvent 事件对象. 在该方法中编写事件的响应处理逻辑.
3.事件广播器
当容器事件发生时, 容器主控程序将调用事件广播器将事件通知给事件监听器注册表中所有的事件监听器. 事件监听器分别对事件进行响应.
Spring 事件体系的具体实现
Spring 在 ApplicationContext 接口的抽象类 abstractApplicationContext 中完成了事件体系的搭建.
abstractApplicationContext 中有一个 applicationEventMulticaster 成员. applicationEventMulticaster 提供了容器监听器的注册表.
在上述代码5处, Spring 初始化事件广播器. 用户可以在配值文件中为容器定义一个自定义的事件广播器. Spring通过反射技术将其注册成容器的事件广播器, 如果没有外部的事件广播器, Spring自动使用 SimpleApplicationEventMulticaster 作为事件广播器.
在7处, Spring 根据反射机制, 从 BeanDefinitionRegistry 中找出所有实现 ApplicationListern 的Bean. 将它们注册为容器的事件监听器. 实际操作就是将它们添加到事件广播提供的事件监听器注册表中.
在9处, 容器启动完成时, 调动事件发布接口向容器中所有的监听器发布事件. 在 publishEvent() 中可以看到, Spring 委托 ApplicationEventMulticaster 将事件通知给事件监听器.
实例演示
MailSendEvent 类继承自 ApplicationEvent 事件类.
MailSendListern 实现了 ApplicationListener 接口. 仅对 MailSendEvent 类型事件进行响应.
在 MailSender类中, 先产生一个 MailSendEvent 事件. 通过 publisherEvent() 向容器中所有事件监听器发布事件.
在配置文件中要对 MailSendListern 监听器和 MailSendEvent 类进行配置.
测试结果如下: