Spring初始化Ioc一

SpringIoc 源码解析基于注解,版本5.1.x

通过Spring上下文初始化bean

注解类  ,AnnotationConfigApplicationContext可以实现基于java配置类(各种注解)来加载Spring上下文,相比于用application.xml更简洁更方便。

package com.jingjing.spring;

import org.springframework.context.annotation.AnnotationConfigApplicationContext;
import org.springframework.context.annotation.ComponentScan;

/**
 * 需要扫描哪些目录下的bean
 * Created by jingjing on 2020/3/7
 */
@ComponentScan("com.jingjing")
public class Test {

    public static void main(String[] args) {

       
        /**
         * 初始化bean init
         * 1.把类扫描出来
         * 2.把bean实例化
         */
        AnnotationConfigApplicationContext context = new AnnotationConfigApplicationContext(Test.class);
        BeanTest beanTest= context.getBean(BeanTest.class);
        System.out.println(beanTest);


    }


}
package com.jingjing.spring;

import org.springframework.stereotype.Component;

/**
 * Created by jingjing  on 2020/3/7
 */
@Component
public class BeanTest{

    public BeanTest() {
        System.out.println("init");
    }

  
}

 AnnotationConfigApplicationContext构造函数

   


        /**
         * 将相应配置类中的bean注册到容器中
         * 创建一个新的注解配置上下文,从annotatedClasses配置类中得到bean definitions,再将
         * bean definition更新到上下文
	 * 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) {
		//由于它有父类,会先调用父类构造方法,再调用自己的构造方法
		//在自己的构造方法中初始化一个读取器和一个扫描器
		//父类构造方法创建一个beanFactory  DefaultListableBeanFactory
		this();
                //把注解类变成一个BeanDefinition
		register(annotatedClasses);
                //扫描类,并把这些路径下的Class变成一个BeanDefinition,再把部分BeanDefinition变成bean对象
		refresh();
	}

this()方法解析 

AnnotationConfigApplicationContext继承于GenericApplicationContext

        /**
         * 父类GenericApplication默认构造函数,创建一个BeanFactory  
         * DefaultListableBeanFactory,一个很重要的BeanFactory
	 * Create a new GenericApplicationContext.
	 * @see #registerBeanDefinition
	 * @see #refresh
	 */
	public GenericApplicationContext() {
		this.beanFactory = new DefaultListableBeanFactory();
	}
     /**
         * 默认构造函数
         * 创建一个基于注解的BeanDefinition读取器
         * 创建一个通过路径扫描BeanDefinition扫描器
	 * Create a new AnnotationConfigApplicationContext that needs to be populated
	 * through {@link #register} calls and then manually {@linkplain #refresh refreshed}.
	 */
	public AnnotationConfigApplicationContext() {
		this.reader = new AnnotatedBeanDefinitionReader(this);
		this.scanner = new ClassPathBeanDefinitionScanner(this);
	}

register(annotatedClasses)方法解析

/**
*实际上是调用AnnotatedBeanDefinitionReader类的register方法
*/
public void register(Class... annotatedClasses) {
		Assert.notEmpty(annotatedClasses, "At least one annotated class must be specified");
		this.reader.register(annotatedClasses);
	}

核心逻辑是AnnotatedBeanDefinition的doRegisterBean()方法

public void register(Class... annotatedClasses) {
		Assert.notEmpty(annotatedClasses, "At least one annotated class must be specified");
		this.reader.register(annotatedClasses);
	}


public void registerBean(Class annotatedClass) {
		doRegisterBean(annotatedClass, null, null, null);
	}

    /**
	 * Register a bean from the given bean class, deriving its metadata from
	 * class-declared annotations.
	 * @param annotatedClass the class of the bean
	 * @param instanceSupplier a callback for creating an instance of the bean
	 * (may be {@code null})
	 * @param name an explicit name for the bean
	 * @param qualifiers specific qualifier annotations to consider, if any,
	 * in addition to qualifiers at the bean class level
	 * @param definitionCustomizers one or more callbacks for customizing the
	 * factory's {@link BeanDefinition}, e.g. setting a lazy-init or primary flag
	 * @since 5.0
	 */
	 void doRegisterBean(Class annotatedClass, @Nullable Supplier instanceSupplier, @Nullable String name,
			@Nullable Class[] qualifiers, BeanDefinitionCustomizer... definitionCustomizers) {

		//将配置类class转变成AnnotatedGenericBeanDefinition,AnnotatedGenericBeanDefinition继承BeanDefinition,
		//作用是定义一个bean的数据结构,getmetadata()可以获取到该bean上的注解信息
		AnnotatedGenericBeanDefinition abd = new AnnotatedGenericBeanDefinition(annotatedClass);
		//@Conditional装配条件判断是否跳过注册
		if (this.conditionEvaluator.shouldSkip(abd.getMetadata())) {
			return;
		}

		//设置回调
		abd.setInstanceSupplier(instanceSupplier);
		//解析bean作用域(单例或原型),如果有@Scope注解就解析bean作用域,没有就默认singleton
		ScopeMetadata scopeMetadata = this.scopeMetadataResolver.resolveScopeMetadata(abd);
		//作用域写回beandefinition中
		abd.setScope(scopeMetadata.getScopeName());
		//生成bean配置类beanName
		String beanName = (name != null ? name : this.beanNameGenerator.generateBeanName(abd, this.registry));
		//通用注解解析到BeanDefinition结构中,主要处理 lazy Primary DependsOn Role Description这五个注解
		AnnotationConfigUtils.processCommonDefinitionAnnotations(abd);
		//@Qualifier特殊限定符处理
		if (qualifiers != null) {
			for (Class qualifier : qualifiers) {
				//如果配置Primary注解,则设置当前bean为自动装配autowire时首选bean
				if (Primary.class == qualifier) {
					abd.setPrimary(true);
				}
				//设置懒加载即延时加载
				else if (Lazy.class == qualifier) {
					abd.setLazyInit(true);
				}
				else {
					//将其他注解添加到abd结构中
					abd.addQualifier(new AutowireCandidateQualifier(qualifier));
				}
			}
		}
		//自定义bean注册,通常用在applicationContext创建后,自己手动像容器中-lambda表达式的方式注册bean
		// applicationContext.registerBean(Test.class,()->new Test());
		for (BeanDefinitionCustomizer customizer : definitionCustomizers) {
			//自定义bean添加到BeanDefinition
			customizer.customize(abd);
		}

		//根据beanName beanDefinition(bean定义信息)封装成一个beanDefinitionHolder
		BeanDefinitionHolder definitionHolder = new BeanDefinitionHolder(abd, beanName);
		//创建代理对象
		definitionHolder = AnnotationConfigUtils.applyScopedProxyMode(scopeMetadata, definitionHolder, this.registry);
		//深入代码内部可以发现最后还是调用DefaultListableBeanFactory的registerBeanDefinition()
		//逻辑是把 beanName,beanDefinition放入BeanFactory的BeanDefinitionMap中
		BeanDefinitionReaderUtils.registerBeanDefinition(definitionHolder, this.registry);
	}

其实register方法主要完成了配置类的解析和注册,主要有以下步骤

1.将配置类annotatedClass,使用BeanDefinition解析Bean的定义信息 ,主要是一些注解信息

2.bean的作用域处理,如果有@Scope作用域就返回作用域,没有就默认为Singleton

3.借助AnnotationConfigUtils解析通用注解

4.将bean定义信息(beanName,BeanDefinition)注册到Ioc容器中

refresh方法解析

refresh()方法在AbstractApplicationContext类中实现,这个类的主要作用就是加载或者刷新当前的配置信息,如果已经存在Spring容器则先销毁之前Spring容器,重新创建Spring容器,载入bean定义,完成容器初始化工作。可以看出AnnotationConfigApplicationContext容器是通过调用其父类AbstractApplicationContext的refresh方法启动整个Ioc容器完成对bean定义的载入和初始化

1.刷新预处理

AbstractApplicationContext.prepareRefresh()

protected void prepareRefresh() {
		// Switch to active.
		//设置容器启动时间
		this.startupDate = System.currentTimeMillis();
		//启动标识
		this.closed.set(false);
		this.active.set(true);

		if (logger.isDebugEnabled()) {
			if (logger.isTraceEnabled()) {
				logger.trace("Refreshing " + this);
			}
			else {
				logger.debug("Refreshing " + getDisplayName());
			}
		}

		// 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.子类刷新内部的BeanFactory并获得刷新的BeanFactory

AbstractApplicationContext.obtainBeanFactory()

/**
 * 告诉子类刷新内部的BeanFactory
 * Tell the subclass to refresh the internal bean factory.
 * @return the fresh BeanFactory instance
 * @see #refreshBeanFactory()
 * @see #getBeanFactory()
 */
protected ConfigurableListableBeanFactory obtainFreshBeanFactory() {
   refreshBeanFactory();
   return getBeanFactory();
}

GenericApplicationContext.refreshBeanFactory和getBeanFactory

protected final void refreshBeanFactory() throws IllegalStateException {
		//用AtomicBoolean的原子操作给refreshed变量赋值,初始化时refreshed是false,如果赋值失败抛出异常,避免多次刷新
		if (!this.refreshed.compareAndSet(false, true)) {
			throw new IllegalStateException(
					"GenericApplicationContext does not support multiple refresh attempts: just call 'refresh' once");
		}
		//给BeanFactory设置序列化id为AnnotationConfigApplicationContext的id唯一标识
		this.beanFactory.setSerializationId(getId());
	}


	public final ConfigurableListableBeanFactory getBeanFactory() {
        //返回DefaultListableBeanFactory
		return this.beanFactory;
	}

刷新BeanFactory的步骤主要如下:

1.给AnnotationConfigApplicationContext的refreshed值设为true

2.给DefaultBeanFactory的serializationId设置值为AnnotationConfigApplicationContext的id值

 

3.BeanFactory预处理

主要完成BeanFactory的属性设置

/**
* 完成BeanFactory的属性设置
*/
protected void prepareBeanFactory(ConfigurableListableBeanFactory beanFactory) {
		// Tell the internal bean factory to use the context's class loader etc.
		//给BeanFactory设置bean类加载器为容器的类加载器
		beanFactory.setBeanClassLoader(getClassLoader());
		//bean表达式解析器
		beanFactory.setBeanExpressionResolver(new StandardBeanExpressionResolver(beanFactory.getBeanClassLoader()));
		//属性编辑注册器
		beanFactory.addPropertyEditorRegistrar(new ResourceEditorRegistrar(this, getEnvironment()));

		// Configure the bean factory with context callbacks.
		//使用上下文回调配置beanFactory
		//添加一个BeanPostProcessor bean后置处理器实现ApplicationContextAwareProcess
		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.
		//注册可以自动装配的组件,在任何组件中允许自动注入的组件
		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.
		// 用应用监听器注册早期的PostProcessor 去检测内部的bean
		beanFactory.addBeanPostProcessor(new ApplicationListenerDetector(this));

		// Detect a LoadTimeWeaver and prepare for weaving, if found.
		//添加编译时的AspectJ
		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.
		//给容器中注册Singleton组件,ConfigurableEnviroment,systemProperties,systemEnvironment,添加到singletonObjects(ConcurrentHashMap类型)中
		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());
		}
	}

5.执行BeanFactoryPostProcess方法,BeanFactory的后置处理器,在beanFactory标准初始化后执行

protected void invokeBeanFactoryPostProcessors(ConfigurableListableBeanFactory beanFactory) {
		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()));
		}
	}
public static void invokeBeanFactoryPostProcessors(
			ConfigurableListableBeanFactory beanFactory, List beanFactoryPostProcessors) {

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

		if (beanFactory instanceof BeanDefinitionRegistry) {
			BeanDefinitionRegistry registry = (BeanDefinitionRegistry) beanFactory;
			List regularPostProcessors = new ArrayList<>();
			List registryProcessors = new ArrayList<>();

			for (BeanFactoryPostProcessor postProcessor : beanFactoryPostProcessors) {
				if (postProcessor instanceof BeanDefinitionRegistryPostProcessor) {
					BeanDefinitionRegistryPostProcessor registryProcessor =
							(BeanDefinitionRegistryPostProcessor) postProcessor;
					registryProcessor.postProcessBeanDefinitionRegistry(registry);
					registryProcessors.add(registryProcessor);
				}
				else {
					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.
			List currentRegistryProcessors = new ArrayList<>();

			// First, invoke the BeanDefinitionRegistryPostProcessors that implement PriorityOrdered.
			String[] postProcessorNames =
					beanFactory.getBeanNamesForType(BeanDefinitionRegistryPostProcessor.class, true, false);
			for (String ppName : postProcessorNames) {
				if (beanFactory.isTypeMatch(ppName, PriorityOrdered.class)) {
					currentRegistryProcessors.add(beanFactory.getBean(ppName, BeanDefinitionRegistryPostProcessor.class));
					processedBeans.add(ppName);
				}
			}
			sortPostProcessors(currentRegistryProcessors, beanFactory);
			registryProcessors.addAll(currentRegistryProcessors);
			invokeBeanDefinitionRegistryPostProcessors(currentRegistryProcessors, registry);
			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.
			invokeBeanFactoryPostProcessors(registryProcessors, beanFactory);
			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!
		String[] postProcessorNames =
				beanFactory.getBeanNamesForType(BeanFactoryPostProcessor.class, true, false);

		// Separate between BeanFactoryPostProcessors that implement PriorityOrdered,
		// Ordered, and the rest.
		List priorityOrderedPostProcessors = new ArrayList<>();
		List orderedPostProcessorNames = new ArrayList<>();
		List 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 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 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();
	}

 

你可能感兴趣的:(Spring)