Spring容器refresh方法执行流程

spring启动过程

onfresh主流程

refresh{
  // Prepare this context for refreshing.
  
 // Prepare this context for refreshing, setting its startup date and active flag as well as performing any initialization of property sources.
  // 设置其启动日期和活动标志以及各种任何属性来源的初始化。 初始化属性主要指,记录ServletContext和ServletConfig的配置属性(来源于web.xml中的ini-param等),
  prepareRefresh();
  // Tell the subclass to refresh the internal bean factory.
  
  ConfigurableListableBeanFactory beanFactory = obtainFreshBeanFactory();
  // Prepare the bean factory for use in this context.
  //创建BeanFactory及加载beanDefination
  prepareBeanFactory(beanFactory);
  try {
     // Allows post-processing of the bean factory in context subclasses.
     postProcessBeanFactory(beanFactory);
     // Invoke factory processors registered as beans in the context.
     invokeBeanFactoryPostProcessors(beanFactory);
     // Register bean processors that intercept bean creation.
     registerBeanPostProcessors(beanFactory);
     // Initialize message source for this context.
     initMessageSource();
     // Initialize event multicaster for this context.
     initApplicationEventMulticaster();
     // Initialize other special beans in specific context subclasses.
     onRefresh();
     // Check for listener beans and register them.
     registerListeners();
     // Instantiate all remaining (non-lazy-init) singletons.
     finishBeanFactoryInitialization(beanFactory);
     // Last step: publish corresponding event.
     finishRefresh();
  }

  catch (BeansException ex) {
     // Destroy already created singletons to avoid dangling resources.
     destroyBeans();
     // Reset 'active' flag.
     cancelRefresh(ex);
     // Propagate exception to caller.
     throw ex;
  }
  finally {
     // Reset common introspection caches in Spring's core, since we
     // might not ever need metadata for singleton beans anymore...
     resetCommonCaches();
}

1 prepareRefresh

设置其启动日期和活动标志以及各种任何属性来源的初始化。 初始化属性主要指,记录ServletContext和ServletConfig的配置属性(来源于web.xml中的ini-param等),

// Switch to active.
this.startupDate = System.currentTimeMillis();
this.closed.set(false);
this.active.set(true);

// Initialize any placeholder property sources in the context environment.
initPropertySources();

// Validate that all properties marked as required are resolvable:
// see ConfigurablePropertyResolver#setRequiredProperties
getEnvironment().validateRequiredProperties();
// Store pre-refresh ApplicationListeners...
if (this.earlyApplicationListeners == null) {
   this.earlyApplicationListeners = new LinkedHashSet<>(this.applicationListeners);
}
else {
   // Reset local application listeners to pre-refresh state.
   this.applicationListeners.clear();
   this.applicationListeners.addAll(this.earlyApplicationListeners);
}
// Allow for the collection of early ApplicationEvents,
// to be published once the multicaster is available...
this.earlyApplicationEvents = new LinkedHashSet<>();

2 obtainFreshBeanFactory

org.springframework.context.support.AbstractApplicationContext#obtainFreshBeanFactory
protected ConfigurableListableBeanFactory obtainFreshBeanFactory() {
		refreshBeanFactory();
		return getBeanFactory();
	}

3 prepareBeanFactory

配置bean的加载器,Resource编辑器, Aware接口依赖忽略,Aware接口后处理器, 手动注册env相关的bean

protected void prepareBeanFactory(ConfigurableListableBeanFactory beanFactory) {
   // Tell the internal bean factory to use the context's class loader etc.
   beanFactory.setBeanClassLoader(getClassLoader());
   beanFactory.setBeanExpressionResolver(new StandardBeanExpressionResolver(beanFactory.getBeanClassLoader()));
   beanFactory.addPropertyEditorRegistrar(new ResourceEditorRegistrar(this, getEnvironment()));

   // Configure the bean factory with context callbacks.
  //ApplicationContextAwareProcessor 和ignoreDependencyInterface刚好配对
  //ignoreDependencyInterface让自动装配接口的set方法失效,不再注入属性,而是使用ApplicationContextAwareProcessor在spring容器回调时代码主动调用set方法设值。
  (这里的“自动装配”跟“@Autowire”无关,这是说xml bean配置中的"default-autowire","autowire"属性“byType"或”byName“.若加了”@Autowire“注解,ignoreDependencyInterface反而无效,即任然会注入属性)。
  
  
   beanFactory.addBeanPostProcessor(new ApplicationContextAwareProcessor(this));
   beanFactory.ignoreDependencyInterface(EnvironmentAware.class);
   beanFactory.ignoreDependencyInterface(EmbeddedValueResolverAware.class);
   beanFactory.ignoreDependencyInterface(ResourceLoaderAware.class);
   beanFactory.ignoreDependencyInterface(ApplicationEventPublisherAware.class);
   beanFactory.ignoreDependencyInterface(MessageSourceAware.class);
   beanFactory.ignoreDependencyInterface(ApplicationContextAware.class);

   // BeanFactory interface not registered as resolvable type in a plain factory.
   // MessageSource registered (and found for autowiring) as a bean.
  //手动注册依赖,防止按照类型注入时,存在多个bean,注入失败。手动注册依赖后,只会使用这里的指定的实例对象
   beanFactory.registerResolvableDependency(BeanFactory.class, beanFactory);
   beanFactory.registerResolvableDependency(ResourceLoader.class, this);
   beanFactory.registerResolvableDependency(ApplicationEventPublisher.class, this);
   beanFactory.registerResolvableDependency(ApplicationContext.class, this);

   // Register early post-processor for detecting inner beans as ApplicationListeners.
  
   beanFactory.addBeanPostProcessor(new ApplicationListenerDetector(this));

   // Detect a LoadTimeWeaver and prepare for weaving, if found.
   if (beanFactory.containsBean(LOAD_TIME_WEAVER_BEAN_NAME)) {
      beanFactory.addBeanPostProcessor(new LoadTimeWeaverAwareProcessor(beanFactory));
      // Set a temporary ClassLoader for type matching.
      beanFactory.setTempClassLoader(new ContextTypeMatchClassLoader(beanFactory.getBeanClassLoader()));
   }

   // Register default environment beans.
   if (!beanFactory.containsLocalBean(ENVIRONMENT_BEAN_NAME)) {
      beanFactory.registerSingleton(ENVIRONMENT_BEAN_NAME, getEnvironment());
   }
   if (!beanFactory.containsLocalBean(SYSTEM_PROPERTIES_BEAN_NAME)) {
      beanFactory.registerSingleton(SYSTEM_PROPERTIES_BEAN_NAME, getEnvironment().getSystemProperties());
   }
   if (!beanFactory.containsLocalBean(SYSTEM_ENVIRONMENT_BEAN_NAME)) {
      beanFactory.registerSingleton(SYSTEM_ENVIRONMENT_BEAN_NAME, getEnvironment().getSystemEnvironment());
   }
}

传统的xml配置的beanDefinition,使用此实现

org.springframework.context.support.AbstractRefreshableApplicationContext#refreshBeanFactory
@Override
protected final void refreshBeanFactory() throws BeansException {
   if (hasBeanFactory()) {
      destroyBeans();
      closeBeanFactory();
   }
      DefaultListableBeanFactory beanFactory = createBeanFactory();
      beanFactory.setSerializationId(getId());
      customizeBeanFactory(beanFactory);
      loadBeanDefinitions(beanFactory);
      this.beanFactory = beanFactory;
}

springboot基于注解,不去加载beanDefinition

org.springframework.context.support.GenericApplicationContext#refreshBeanFactory
@Override
protected final void refreshBeanFactory() throws IllegalStateException {
   if (!this.refreshed.compareAndSet(false, true)) {
      throw new IllegalStateException(
            "GenericApplicationContext does not support multiple refresh attempts: just call 'refresh' once");
   }
   this.beanFactory.setSerializationId(getId());
}

4 postProcessBeanFactory

调用容器中所有BeanFactoryPostProcessor的postProcessBeanFactory方法。

9 onRefresh

在springmvc的(root)父容器是空实现(AbstractApplicationContext#onRefresh方法),(Web)子容器如下(GenericWebApplicationContext#onRefresh),

在springboot框架中,Servlet Web环境 (Web)子容器会启动内嵌的web容器,入tomcat和jetty.

在Reative Web环境(Web)子容器启动netty作为web server


org.springframework.web.context.support.GenericWebApplicationContext#onRefresh
@Override
	protected void onRefresh() {
		this.themeSource = UiApplicationContextUtils.initThemeSource(this);
	}

  ServletWebServerApplicationContext#onRefresh
  protected void onRefresh()  onRefresh(){
  super.onRefresh();//GenericWebApplicationContext的onRefresh
		try {
			createWebServer();//springboot创建容器 web
		}
}
org.springframework.boot.web.reactive.context.ReactiveWebServerApplicationContext#onRefresh
	@Override
	protected void onRefresh() {
		super.onRefresh();
		try {
			createWebServer();
		}
		catch (Throwable ex) {
			throw new ApplicationContextException("Unable to start reactive web server", ex);
		}
	}
  

你可能感兴趣的:(框架,spring,java,后端)