以代码流程方式探索Spring源码--初始化事件管理类及注册事件类
入口还是在refresh()方法中
初始化事件管理器initApplicationEventMulticaster()
首先获取beanFactory实例,这里返回的就是DefaultListableBeanFactory实例。
判断容器中是否有名字是 applicationEventMulticaster 的BeanDefinition,有的话就通过getBean()方法实例化该Bean。(第一次进来没有的话,第二次进来就有了)
没有的话就New一个SimpleApplicationEventMulticaster,并注册到容器中。
onRefresh()方法
留给用户新建子类来扩展该方法,是一个钩子方法。
往事件管理类中注册事件类registerListeners()
如上图的1所示,是通过getApplicationListeners()方法获得的监听器。而2是通过对bean判断是否实现了ApplicationListener接口来收集的。
这里的get方法取到的applicationListeners有一个public的add方法,可以获得AbstractApplicationContext的实例后进行调用进行add。
上面这两种方式的getApplicationEventMulticaster()方法返回的就是我们之前初始化的事件管理器。
而addApplicationListener()方法和addApplicationListenerBean()方法是将listen加入到类AbstractApplicationEventMulticaster的内部类ListenerRetriever的对应的两个List中。
在将事件监听器加入进去后,会通过getApplicationEventMulticaster().multicastEvent()方法进行方法的调用。
这个onApplicationEvent(event)方法就是实现ApplicationEvent接口所需实现的业务类。
举个栗子
自定义的Listener类,实现了ApplicationListener接口,重新实现了onApplicationEvent()方法来实现自定义的业务逻辑。
自定义事件类,实现了父类ApplicationEvent。
上图中的两个addApplicationListener()方法可以在往前文所说的那个类变量List中加入监听器。
publishEvent()方法会发布事件Event,跟进去发现走的逻辑也是上一步介绍的getApplicationEventMulticaster().multicastEvent()方法来调用自定义实现逻辑。
跟进start()方法和stop()方法,发现分别是发布了新建的ContextStartedEvent()和ContextStoppedEvent()。
Spring提供的五种标准事件
1、上下文更新事件(ContextRefreshedEvent):在调用ConfigurableApplicationContext接口中的refresh()方法时被触发。
2、上下文开始事件(ContextStartedEvent):当容器调用ConfigurableApplicationContext的start()方法开始/重新开始容器时触发该事件。
3、上下文停止事件(ContextStoppedEvent):当容器调用ConfigurableApplicationContext的stop()方法开始/重新开始容器时触发该事件。
4、上下文关闭事件(ContextClosedEvent):当ApplicationContext被关闭时触发该事件,容器被关闭时,其管理的所有单例Bean都被销毁。
5、请求处理事件(RequestHandledEvent):在web应用中,当一个http请求(request)结束触发该事件。
如果一个Bean实现了ApplicationListener接口,当一个ApplicationEvent被发布以后,bean会自动被通知。
补充一点
在refresh()中的最后一个方法是finishRefresh()方法,在该方法中,spring发布了ContextRefreshedEvent事件,这个时候自定义的实现了ApplicationListener<ContextRefreshedEvent>的自定义类的重写方法onApplicationEvent的自定义逻辑会被执行。