多应用+插件架构,代码干净,二开方便,首家独创一键云编译技术,文档视频完善,免费商用码云13.8K 广告
## Lifecycle ~~~java public interface Lifecycle { void start(); void stop(); boolean isRunning(); } ~~~ LifeCycle定义Spring容器对象的生命周期,任何spring管理对象都可以实现该接口。 当ApplicationContext本身接收启动和停止信号(例如在运行时停止/重启场景)时,spring容器将在容器上下文中找出所有实现了LifeCycle及其子类接口的类,并一一调用它们实现的类。spring是通过委托给生命周期处理器LifecycleProcessor来实现这一点的。 #### Lifecycly的不足 常规的Lifecycle接口只是在容器上下文**显式**的调用start()/stop()方法时,才会去回调Lifecycle的实现类的start stop方法逻辑。并不意味着在上下文刷新时自动启动。 ~~~java public class HelloLifeCycle implements Lifecycle { private volatile boolean running = false; public HelloLifeCycle() { System.out.println("构造方法!!!"); } @Override public void start() { System.out.println("lifycycle start"); running = true; } @Override public void stop() { System.out.println("lifycycle stop"); running = false; } @Override public boolean isRunning() { return running; } } ~~~ ~~~java @SpringBootApplication public class EurekaClientApplication { public static void main(String[] args) { SpringApplication.run(EurekaClientApplication.class, args); } } ~~~ 结果是,控制台没有任何输出,容器并没有调用生命周期的回调方法。 当我们将启动容器的类,显式的加上start和stop方法后: ~~~java @SpringBootApplication public class EurekaClientApplication { public static void main(String[] args) { ConfigurableApplicationContext applicationContext = SpringApplication.run(EurekaClientApplication.class, args); applicationContext.start(); applicationContext.stop(); } } ~~~ 这时我们看控制台,spring容器回调了生命周期的方法 ~~~java 2020-12-27 22:40:18.312 INFO 12152 --- [ main] o.s.web.context.ContextLoader : Root WebApplicationContext: initialization completed in 1664 ms 构造方法!!! 2020-12-27 22:40:18.691 INFO 12152 --- [ main] o.s.s.concurrent.ThreadPoolTaskExecutor : Initializing ExecutorService 'applicationTaskExecutor' lifycycle start 2020-12-27 22:40:19.107 INFO 12152 --- [ main] o.s.b.w.embedded.tomcat.TomcatWebServer : Tomcat started on port(s): 8086 (http) with context path '' 2020-12-27 22:40:19.112 INFO 12152 --- [ main] c.e.e.EurekaClientApplication : Started EurekaClientApplication in 3.44 seconds (JVM running for 4.891) lifycycle stop ~~~ ## LifecycleProcessor LifecycleProcessor 负责管理ApplicationContext生命周期。是ApplicationContext很重要的一环,需要他的地方实在太多了。 LifecycleProcessor的onRefresh与onClose是比较重要的方法,onRefresh作用是容器启动成功,onClose是只应用要关闭的时候。 请注意,LifecycleProcessor本身就是LifeCycle接口的扩展。它还添加了另外两个方法来响应spring容器上下文的刷新(onRefresh)和关闭(close)。 ~~~java public interface LifecycleProcessor extends Lifecycle { void onRefresh(); void onClose(); } ~~~ ## DefaultLifecycleProcessor DefaultLifecycleProcessor 是默认LifecycleProcessor实现,主要是负责所有的LifecycleProcessor实现执行,DefaultLifecycleProcessor是LifecycleProcessor的代理对象。 ### 初始化LifecycleProcessor AbstractApplicationContext#initLifecycleProcessor() ~~~java /** * 初始化LifecycleProcessor,如果上下文中没有LifecycleProcessor的实现类, * 就使用DefaultLifecycleProcessor作为LifecycleProcessor默认实现 * Initialize the LifecycleProcessor. * Uses DefaultLifecycleProcessor if none defined in the context. * @see org.springframework.context.support.DefaultLifecycleProcessor */ protected void initLifecycleProcessor() { ConfigurableListableBeanFactory beanFactory = getBeanFactory(); if (beanFactory.containsLocalBean(LIFECYCLE_PROCESSOR_BEAN_NAME)) { this.lifecycleProcessor = beanFactory.getBean(LIFECYCLE_PROCESSOR_BEAN_NAME, LifecycleProcessor.class); if (logger.isTraceEnabled()) { logger.trace("Using LifecycleProcessor [" + this.lifecycleProcessor + "]"); } } else { DefaultLifecycleProcessor defaultProcessor = new DefaultLifecycleProcessor(); defaultProcessor.setBeanFactory(beanFactory); this.lifecycleProcessor = defaultProcessor; beanFactory.registerSingleton(LIFECYCLE_PROCESSOR_BEAN_NAME, this.lifecycleProcessor); if (logger.isTraceEnabled()) { logger.trace("No '" + LIFECYCLE_PROCESSOR_BEAN_NAME + "' bean, using " + "[" + this.lifecycleProcessor.getClass().getSimpleName() + "]"); } } } ~~~ **从beanFactory获得LifecycleProcessor实现类** ~~~java /** * 获取所有实现了 Lifecycle 和 SmartLifecycle 的类 * Retrieve all applicable Lifecycle beans: all singletons that have already been created, * as well as all SmartLifecycle beans (even if they are marked as lazy-init). * @return the Map of applicable beans, with bean names as keys and bean instances as values */ protected Map<String, Lifecycle> getLifecycleBeans() { ConfigurableListableBeanFactory beanFactory = getBeanFactory(); Map<String, Lifecycle> beans = new LinkedHashMap<>(); // 获取所有实现了Lifecycle接口的类 String[] beanNames = beanFactory.getBeanNamesForType(Lifecycle.class, false, false); for (String beanName : beanNames) { String beanNameToRegister = BeanFactoryUtils.transformedBeanName(beanName); boolean isFactoryBean = beanFactory.isFactoryBean(beanNameToRegister); String beanNameToCheck = (isFactoryBean ? BeanFactory.FACTORY_BEAN_PREFIX + beanName : beanName); if ((beanFactory.containsSingleton(beanNameToRegister) && (!isFactoryBean || matchesBeanType(Lifecycle.class, beanNameToCheck, beanFactory))) || matchesBeanType(SmartLifecycle.class, beanNameToCheck, beanFactory)) { Object bean = beanFactory.getBean(beanNameToCheck); if (bean != this && bean instanceof Lifecycle) { beans.put(beanNameToRegister, (Lifecycle) bean); } } } return beans; } ~~~ 获取到所有的SmartLifecycle实现类,且如果autoStartupOnly()方法返回true,则执行SmartLifecycle实现类的start()方法 ~~~java /** * Start the specified bean as part of the given set of Lifecycle beans, * making sure that any beans that it depends on are started first. * @param lifecycleBeans a Map with bean name as key and Lifecycle instance as value * @param beanName the name of the bean to start */ private void doStart(Map<String, ? extends Lifecycle> lifecycleBeans, String beanName, boolean autoStartupOnly) { Lifecycle bean = lifecycleBeans.remove(beanName); if (bean != null && bean != this) { String[] dependenciesForBean = getBeanFactory().getDependenciesForBean(beanName); for (String dependency : dependenciesForBean) { doStart(lifecycleBeans, dependency, autoStartupOnly); } if (!bean.isRunning() && (!autoStartupOnly || !(bean instanceof SmartLifecycle) || ((SmartLifecycle) bean).isAutoStartup())) { if (logger.isTraceEnabled()) { logger.trace("Starting bean '" + beanName + "' of type [" + bean.getClass().getName() + "]"); } try { // 调用Lifecycle的start()方法 bean.start(); } catch (Throwable ex) { throw new ApplicationContextException("Failed to start bean '" + beanName + "'", ex); } if (logger.isDebugEnabled()) { logger.debug("Successfully started bean '" + beanName + "'"); } } } } ~~~ LifecycleProcessor生命周期大致流程图如下: ![](https://img.kancloud.cn/c6/7c/c67cb418d3839cfa056c863b3b859414_1281x1128.png)