天天看點

Spring源碼解析--階段總結(BeanFactory初始化)

前幾篇文章,總結了幾個重要的知識,比如:

BeanPostProcessor

BeanFactoryPostProcessor

BeanDefinitionRegisterPostProcessor

ImportSelector

ImportBeanDefinitionRegistrar

ConfigurationClassPostProcessor

這篇來統一彙總一下:

BeanPostProcessor

插手bean的執行個體化過程,執行個體化之後,在bean沒有被spring的Bean容器管理之前工作,

經典應用場景: aop,@PostConstruct

BeanFactoryPostProcessor

spring的bean容器當中任意一個類被new出來之前執行,針對BeanFactory建設,

場景:ConfigurationClassPostProcessor類繼承這個接口,并且重寫#PostProcessorBeanFactory方法,針對全配置類加上cjlib代理

BeanDefinitionRegistryPostProcessor

此接口繼承了BeanFactoryPostProcessor接口,在BeanFactoryPostProcessor之前執行;

因為,源碼當中是先周遊了BeanDefinitionRegistryPostProcessor(有spring自己提供的,還有自定義的,且自定義的先執行),

ConfigurationClassPostProcessor中的#postProcessBeanDefinitionRegistry()方法,解析@ComponentScan,3中@Import,@Bean,判斷配置類是否是一個完整的配置類......

ImportSelector 接口,某個類通過實作這個接口,override#SelectImports()方法,傳回要注冊Bean的類名,(全限定名),并把這個類變成bd,動态添加bd,(這個bd此時還沒有變成bean,是死的。)
ImportBeanDefinitionRegistrar

# RegisterBeanDefinitions()方法,可以得到BeanDefinitionRegistry,故而可以動态添加bd,并且可以改變bd,

應用場景:Mybatis中的MapperScan   

spring源碼:從AnnotationConfigApplicationContext的有參構造方法開始:(詳細解釋都在源碼注釋裡了)

public class Test {

    public static void main(String[] args) {
        AnnotationConfigApplicationContext annotationConfigApplicationContext=
                new AnnotationConfigApplicationContext(Appconfig.class);
       // annotationConfigApplicationContext.register(Appconfig.class);
       // annotationConfigApplicationContext.refresh();
        System.out.println(annotationConfigApplicationContext.getBean(TestDao.class).hashCode());
        //System.out.println(annotationConfigApplicationContext.getBean(TestDao.class).hashCode());
    }
}
           
/**
	 * Create a new AnnotationConfigApplicationContext with the given     
       DefaultListableBeanFactory.
	 * @param beanFactory the DefaultListableBeanFactory instance to use for this context
	 */
	public AnnotationConfigApplicationContext(DefaultListableBeanFactory beanFactory) {
		super(beanFactory);
		this.reader = new AnnotatedBeanDefinitionReader(this);
		this.scanner = new ClassPathBeanDefinitionScanner(this);
	}
     /**
	 * 這個構造方法需要傳入一個被javaconfig注解了的配置類
	 * 然後會把這個被注解了javaconfig的類通過注解讀取器讀取後繼而解析
	 * Create a new AnnotationConfigApplicationContext, deriving bean definitions
	 * from the given annotated classes and automatically refreshing the context.
	 * @param annotatedClasses one or more annotated classes,
	 * e.g. {@link Configuration @Configuration} classes
	 */
	public AnnotationConfigApplicationContext(Class<?>... annotatedClasses) {
		//annotatedClasses  appconfig.class
		//這裡由于他有父類,故而會先調用父類的構造方法,然後才會調用自己的構造方法
		//在自己構造方法中初始一個讀取器和掃描器
		this();
		register(annotatedClasses);
		refresh();
	}
           

跟蹤refresh()方法進入:(AbstractApplicationContext類中)

@Override
	public void refresh() throws BeansException, IllegalStateException {
		synchronized (this.startupShutdownMonitor) {
			// Prepare this context for refreshing.
			//準備工作包括設定啟動時間,是否激活辨別位,
			// 初始化屬性源(property source)配置
			prepareRefresh();

			// Tell the subclass to refresh the internal bean factory.
			//傳回一個factory 為什麼需要傳回一個工廠
			//因為要對工廠進行初始化
			ConfigurableListableBeanFactory beanFactory = obtainFreshBeanFactory();

			// Prepare the bean factory for use in this context.
			//準備工廠
			prepareBeanFactory(beanFactory);

			try {
				// Allows post-processing of the bean factory in context subclasses.

				//這個方法在目前版本的spring是沒用任何代碼的
				//可能spring期待在後面的版本中去擴充吧
				postProcessBeanFactory(beanFactory);

				// Invoke factory processors registered as beans in the context.
				//在spring的環境中去執行已經被注冊的 factory processors
				//設定執行自定義的ProcessBeanFactory 和spring内部自己定義的
				invokeBeanFactoryPostProcessors(beanFactory);

				// Register bean processors that intercept bean creation.
				//注冊beanPostProcessor
				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) {
				if (logger.isWarnEnabled()) {
					logger.warn("Exception encountered during context initialization - " +
							"cancelling refresh attempt: " + 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();
			}
		}
	}

//xxxx其他方法......
           

invokeBeanFactoryPostProcessors(beanFactory);

protected void invokeBeanFactoryPostProcessors(ConfigurableListableBeanFactory beanFactory) {
		//這個地方需要注意getBeanFactoryPostProcessors()是擷取手動給spring的BeanFactoryPostProcessor
		//自定義并不僅僅是程式員自己寫的
		//自己寫的可以加companent也可以不加
		//如果加了getBeanFactoryPostProcessors()這個地方得不得,是spring自己掃描的
		//為什麼得不到getBeanFactoryPostProcessors()這個方法是直接擷取一個list,
		//這個list是在AnnotationConfigApplicationContext被定義
		//所謂的自定義的就是你手動調用AnnotationConfigApplicationContext.addBeanFactoryPostProcesor();


		PostProcessorRegistrationDelegate.invokeBeanFactoryPostProcessors(beanFactory, getBeanFactoryPostProcessors());

		// Detect a LoadTimeWeaver and prepare for weaving, if found in the meantime
		// (e.g. through an @Bean method registered by ConfigurationClassPostProcessor)
		if (beanFactory.getTempClassLoader() == null && beanFactory.containsBean(LOAD_TIME_WEAVER_BEAN_NAME)) {
			beanFactory.addBeanPostProcessor(new LoadTimeWeaverAwareProcessor(beanFactory));
			beanFactory.setTempClassLoader(new ContextTypeMatchClassLoader(beanFactory.getBeanClassLoader()));
		}
	}
           

    PostProcessorRegistrationDelegate.invokeBeanFactoryPostProcessors(beanFactory, getBeanFactoryPostProcessors());

public static void invokeBeanFactoryPostProcessors(
			ConfigurableListableBeanFactory beanFactory, List<BeanFactoryPostProcessor> beanFactoryPostProcessors) {

		// Invoke BeanDefinitionRegistryPostProcessors first, if any.
		Set<String> processedBeans = new HashSet<>();

		if (beanFactory instanceof BeanDefinitionRegistry) {
			BeanDefinitionRegistry registry = (BeanDefinitionRegistry) beanFactory;

			List<BeanFactoryPostProcessor> regularPostProcessors = new ArrayList<>();
			List<BeanDefinitionRegistryPostProcessor> registryProcessors = new ArrayList<>();

			//自定義的beanFactoryPostProcessors
			for (BeanFactoryPostProcessor postProcessor : beanFactoryPostProcessors) {
				if (postProcessor instanceof BeanDefinitionRegistryPostProcessor) {
					BeanDefinitionRegistryPostProcessor registryProcessor =
							(BeanDefinitionRegistryPostProcessor) postProcessor;
					registryProcessor.postProcessBeanDefinitionRegistry(registry);
					registryProcessors.add(registryProcessor);
				}
				else {//BeanDefinitionRegistryPostProcessor  BeanfactoryPostProcessor
					regularPostProcessors.add(postProcessor);
				}
			}

			// Do not initialize FactoryBeans here: We need to leave all regular beans
			// uninitialized to let the bean factory post-processors apply to them!
			// Separate between BeanDefinitionRegistryPostProcessors that implement
			// PriorityOrdered, Ordered, and the rest.

			//這個currentRegistryProcessors 放的是spring内部自己實作了BeanDefinitionRegistryPostProcessor接口的對象

			List<BeanDefinitionRegistryPostProcessor> currentRegistryProcessors = new ArrayList<>();

			// First, invoke the BeanDefinitionRegistryPostProcessors that implement PriorityOrdered.
			//BeanDefinitionRegistryPostProcessor 等于 BeanFactoryPostProcessor
			//getBeanNamesForType  根據bean的類型擷取bean的名字=ConfigurationClassPostProcessor
			String[] postProcessorNames =
					beanFactory.getBeanNamesForType(BeanDefinitionRegistryPostProcessor.class,true, false);
			//這個地方可以得到一個BeanFactoryPostProcessor,因為是spring預設在最開始自己注冊的BeanDefinitionRegistryPostProcessor.class,
			//為什麼要在最開始注冊這個呢?
			//因為spring的工廠需要去解析注解  去掃描等等功能
			//而這些功能都是需要在spring工廠初始化完成之前執行
			//要麼在工廠最開始的時候、要麼在工廠初始化之中,反正不能再之後
			//因為如果在之後就沒有意義,因為那個時候已經需要使用工廠了
			//是以這裡spring'在一開始就注冊了一個BeanFactoryPostProcessor,用來插手springfactory的執行個體化過程
			//在這個地方斷點可以知道這個類叫做ConfigurationClassPostProcessor
			//ConfigurationClassPostProcessor那麼這個類能幹嘛呢?可以參考源碼
			//下面我們對這個牛逼哄哄的類(他能插手spring工廠的執行個體化過程還不牛逼嗎?)重點解釋
			for (String ppName : postProcessorNames) {
				if (beanFactory.isTypeMatch(ppName, PriorityOrdered.class)) {
					currentRegistryProcessors.add(beanFactory.getBean(ppName, BeanDefinitionRegistryPostProcessor.class));
					processedBeans.add(ppName);
				}
			}
			//排序不重要,況且currentRegistryProcessors這裡也隻有一個資料
			sortPostProcessors(currentRegistryProcessors, beanFactory);
			//合并list,不重要(為什麼要合并,因為還有自己的)
			registryProcessors.addAll(currentRegistryProcessors);
			//最重要。注意這裡是方法調用
			//執行所有BeanDefinitionRegistryPostProcessor

			invokeBeanDefinitionRegistryPostProcessors(currentRegistryProcessors, registry);
			//執行完成了所有BeanDefinitionRegistryPostProcessor
			//這個list隻是一個臨時變量,故而要清除
			currentRegistryProcessors.clear();

			// Next, invoke the BeanDefinitionRegistryPostProcessors that implement Ordered.
			postProcessorNames = beanFactory.getBeanNamesForType(BeanDefinitionRegistryPostProcessor.class, true, false);
			for (String ppName : postProcessorNames) {
				if (!processedBeans.contains(ppName) && beanFactory.isTypeMatch(ppName, Ordered.class)) {
					currentRegistryProcessors.add(beanFactory.getBean(ppName, BeanDefinitionRegistryPostProcessor.class));
					processedBeans.add(ppName);
				}
			}
			sortPostProcessors(currentRegistryProcessors, beanFactory);
			registryProcessors.addAll(currentRegistryProcessors);
			invokeBeanDefinitionRegistryPostProcessors(currentRegistryProcessors, registry);
			currentRegistryProcessors.clear();

			// Finally, invoke all other BeanDefinitionRegistryPostProcessors until no further ones appear.
			boolean reiterate = true;
			while (reiterate) {
				reiterate = false;
				postProcessorNames = beanFactory.getBeanNamesForType(BeanDefinitionRegistryPostProcessor.class, true, false);
				for (String ppName : postProcessorNames) {
					if (!processedBeans.contains(ppName)) {
						currentRegistryProcessors.add(beanFactory.getBean(ppName, BeanDefinitionRegistryPostProcessor.class));
						processedBeans.add(ppName);
						reiterate = true;
					}
				}
				sortPostProcessors(currentRegistryProcessors, beanFactory);
				registryProcessors.addAll(currentRegistryProcessors);
				invokeBeanDefinitionRegistryPostProcessors(currentRegistryProcessors, registry);
				currentRegistryProcessors.clear();
			}

			// Now, invoke the postProcessBeanFactory callback of all processors handled so far.
			//執行BeanFactoryPostProcessor的回調,前面不是嗎?
			//前面執行的BeanFactoryPostProcessor的子類BeanDefinitionRegistryPostProcessor的回調
			//這是執行的是BeanFactoryPostProcessor    postProcessBeanFactory
			//ConfigurationClassPostProcessor
			invokeBeanFactoryPostProcessors(registryProcessors, beanFactory);
			//自定義BeanFactoryPostProcessor
			invokeBeanFactoryPostProcessors(regularPostProcessors, beanFactory);
		}

		else {
			// Invoke factory processors registered with the context instance.
			invokeBeanFactoryPostProcessors(beanFactoryPostProcessors, beanFactory);
		}

		// Do not initialize FactoryBeans here: We need to leave all regular beans
		// uninitialized to let the bean factory post-processors apply to them!
		//ConfigurationClassPostProcessor
		String[] postProcessorNames =
				beanFactory.getBeanNamesForType(BeanFactoryPostProcessor.class, true, false);

		// Separate between BeanFactoryPostProcessors that implement PriorityOrdered,
		// Ordered, and the rest.
		List<BeanFactoryPostProcessor> priorityOrderedPostProcessors = new ArrayList<>();
		List<String> orderedPostProcessorNames = new ArrayList<>();
		List<String> nonOrderedPostProcessorNames = new ArrayList<>();
		for (String ppName : postProcessorNames) {
			if (processedBeans.contains(ppName)) {
				// skip - already processed in first phase above
			}
			else if (beanFactory.isTypeMatch(ppName, PriorityOrdered.class)) {
				priorityOrderedPostProcessors.add(beanFactory.getBean(ppName, BeanFactoryPostProcessor.class));
			}
			else if (beanFactory.isTypeMatch(ppName, Ordered.class)) {
				orderedPostProcessorNames.add(ppName);
			}
			else {
				nonOrderedPostProcessorNames.add(ppName);
			}
		}

		// First, invoke the BeanFactoryPostProcessors that implement PriorityOrdered.
		sortPostProcessors(priorityOrderedPostProcessors, beanFactory);
		invokeBeanFactoryPostProcessors(priorityOrderedPostProcessors, beanFactory);

		// Next, invoke the BeanFactoryPostProcessors that implement Ordered.
		List<BeanFactoryPostProcessor> orderedPostProcessors = new ArrayList<>();
		for (String postProcessorName : orderedPostProcessorNames) {
			orderedPostProcessors.add(beanFactory.getBean(postProcessorName, BeanFactoryPostProcessor.class));
		}
		sortPostProcessors(orderedPostProcessors, beanFactory);
		invokeBeanFactoryPostProcessors(orderedPostProcessors, beanFactory);

		// Finally, invoke all other BeanFactoryPostProcessors.
		List<BeanFactoryPostProcessor> nonOrderedPostProcessors = new ArrayList<>();
		for (String postProcessorName : nonOrderedPostProcessorNames) {
			nonOrderedPostProcessors.add(beanFactory.getBean(postProcessorName, BeanFactoryPostProcessor.class));
		}
		invokeBeanFactoryPostProcessors(nonOrderedPostProcessors, beanFactory);

		// Clear cached merged bean definitions since the post-processors might have
		// modified the original metadata, e.g. replacing placeholders in values...
		beanFactory.clearMetadataCache();
	}
           

           //ConfigurationClassPostProcessor

            invokeBeanFactoryPostProcessors(registryProcessors, beanFactory); 

/**
	 * Invoke the given BeanFactoryPostProcessor beans.
	 */
	private static void invokeBeanFactoryPostProcessors(
			Collection<? extends BeanFactoryPostProcessor> postProcessors, ConfigurableListableBeanFactory beanFactory) {

		for (BeanFactoryPostProcessor postProcessor : postProcessors) {
			postProcessor.postProcessBeanFactory(beanFactory);
		}
	}
           

繼續閱讀