03_spring_依赖来源

注:以下内容为学习《小马哥讲Spring核心编程思想》的个人笔记

依赖查找的来源

查找来源

来源配置元数据
Spring BeanDefinition用户来定义,例如xml配置,注解配置或者通过API来调用。总而言之,是用户来构建BeanDefinition的,例如

@Bean public User user(){…}
BeanDefinitionBuilder
单例对象spring 内置的一些BeanDefinition,通常通过API实现

Spring 內建 BeanDefintion

Bean名称Bean 实例使用场景
internalConfigurationAnnotationProcessorConfigurationClassPostProcessor对象处理 Spring 配置类
internalAutowiredAnnotationProcessorAutowiredAnnotationBeanPostProcessor 对象处理 @Autowired 以及@Value 注解
internalCommonAnnotationProcessorCommonAnnotationBeanPostProcessor 对象(条件激活)处理 JSR-250 注解,如@PostConstruct 等
internalEventListenerProcessorEventListenerMethodProcessor 对 象处理标注 @EventListener 的Spring 事件监听方法

定义源码见:org.springframework.context.annotation.AnnotationConfigUtils#registerAnnotationConfigProcessors

public static Set<BeanDefinitionHolder> registerAnnotationConfigProcessors(
			BeanDefinitionRegistry registry, @Nullable Object source) {

		DefaultListableBeanFactory beanFactory = unwrapDefaultListableBeanFactory(registry);
		if (beanFactory != null) {
			if (!(beanFactory.getDependencyComparator() instanceof AnnotationAwareOrderComparator)) {
				beanFactory.setDependencyComparator(AnnotationAwareOrderComparator.INSTANCE);
			}
			if (!(beanFactory.getAutowireCandidateResolver() instanceof ContextAnnotationAutowireCandidateResolver)) {
				beanFactory.setAutowireCandidateResolver(new ContextAnnotationAutowireCandidateResolver());
			}
		}

		Set<BeanDefinitionHolder> beanDefs = new LinkedHashSet<>(8);

		if (!registry.containsBeanDefinition(CONFIGURATION_ANNOTATION_PROCESSOR_BEAN_NAME)) {
			RootBeanDefinition def = new RootBeanDefinition(ConfigurationClassPostProcessor.class);
			def.setSource(source);
			beanDefs.add(registerPostProcessor(registry, def, CONFIGURATION_ANNOTATION_PROCESSOR_BEAN_NAME));
		}

		if (!registry.containsBeanDefinition(AUTOWIRED_ANNOTATION_PROCESSOR_BEAN_NAME)) {
			RootBeanDefinition def = new RootBeanDefinition(AutowiredAnnotationBeanPostProcessor.class);
			def.setSource(source);
			beanDefs.add(registerPostProcessor(registry, def, AUTOWIRED_ANNOTATION_PROCESSOR_BEAN_NAME));
		}

		// Check for JSR-250 support, and if present add the CommonAnnotationBeanPostProcessor.
		if (jsr250Present && !registry.containsBeanDefinition(COMMON_ANNOTATION_PROCESSOR_BEAN_NAME)) {
			RootBeanDefinition def = new RootBeanDefinition(CommonAnnotationBeanPostProcessor.class);
			def.setSource(source);
			beanDefs.add(registerPostProcessor(registry, def, COMMON_ANNOTATION_PROCESSOR_BEAN_NAME));
		}

		// Check for JPA support, and if present add the PersistenceAnnotationBeanPostProcessor.
		if (jpaPresent && !registry.containsBeanDefinition(PERSISTENCE_ANNOTATION_PROCESSOR_BEAN_NAME)) {
			RootBeanDefinition def = new RootBeanDefinition();
			try {
				def.setBeanClass(ClassUtils.forName(PERSISTENCE_ANNOTATION_PROCESSOR_CLASS_NAME,
						AnnotationConfigUtils.class.getClassLoader()));
			}
			catch (ClassNotFoundException ex) {
				throw new IllegalStateException(
						"Cannot load optional framework class: " + PERSISTENCE_ANNOTATION_PROCESSOR_CLASS_NAME, ex);
			}
			def.setSource(source);
			beanDefs.add(registerPostProcessor(registry, def, PERSISTENCE_ANNOTATION_PROCESSOR_BEAN_NAME));
		}

		if (!registry.containsBeanDefinition(EVENT_LISTENER_PROCESSOR_BEAN_NAME)) {
			RootBeanDefinition def = new RootBeanDefinition(EventListenerMethodProcessor.class);
			def.setSource(source);
			beanDefs.add(registerPostProcessor(registry, def, EVENT_LISTENER_PROCESSOR_BEAN_NAME));
		}

		if (!registry.containsBeanDefinition(EVENT_LISTENER_FACTORY_BEAN_NAME)) {
			RootBeanDefinition def = new RootBeanDefinition(DefaultEventListenerFactory.class);
			def.setSource(source);
			beanDefs.add(registerPostProcessor(registry, def, EVENT_LISTENER_FACTORY_BEAN_NAME));
		}

		return beanDefs;
	}

Spring 內建单例对象

Bean名称Bean实例使用场景
environmentEnvironment 对象外部化配置以及 Profiles
systemPropertiesjava.util.Properties 对象Java 系统属性
systemEnvironmentjava.util.Map 对象操作系统环境变量
messageSourceMessageSource 对象国际化文案
lifecycleProcessorLifecycleProcessor 对象Lifecycle Bean 处理器
applicationEventMulticasterApplicationEventMulticaster 对Spring 事件广播器

上述的内建的单例对象都是通过API调用进行注册,源码可见

org.springframework.context.support.AbstractApplicationContext#createEnvironment

org.springframework.context.support.AbstractApplicationContext#initMessageSource

org.springframework.context.support.AbstractApplicationContext#initLifecycleProcessor

org.springframework.context.support.AbstractApplicationContext#initApplicationEventMulticaster

个人总结

总之,依赖查找来源要么是用户来创建(日常使用中写的Service),要么是spring内置中的创建(例如上述中内置的Bean)。而Spring内置中创建有两种方式,一种是创建BeanDefintion,然后通过BeanDefintion创建。一种是直接通过构造方法(new一个),然后调用**beanFactory.registerSingleton();**来进行创建。

依赖注入的来源

注入来源

来源配置元数据
Spring BeanDefinition用户来定义,例如xml配置,注解配置或者通过API来调用。总而言之,是用户来构建BeanDefinition的,例如

@Bean public User user(){…}
BeanDefinitionBuilder
单例对象spring 内置的一些BeanDefinition,通常通过API实现
非Spring容器管理对象

非Spring容器管理对象通过**beanFactory.registerResolvableDependency();**来创建,通过该接口创建的对象,在依赖查找(beanFactory.getBean())中查找不到,但是依赖注入(@Autowire)时可以进行注入。内置的调用见源码:

/**
	org.springframework.context.support.AbstractApplicationContext#prepareBeanFactory 
	 */
	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.
		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.
		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());
		}
	}

Spring 容器管理和游离对象

来源Spring Bean对象生命周期管理配置元信息使用场景
Spring BeanDefinition依赖查找,依赖注入
单体对象依赖查找,依赖注入
Resolvable Dependency依赖注入
  • Spring BeanDefinition:通过 BeanDefinition 来创建的对象是有配置元信息的,因为BeanDefinition 就是它的配置元信息。作为用户定义的Bean(例如日常代码中的service),当然是Spring Bean对象,接受spring对它的生命周期管理。
  • 单体对象:指的是 Spring 中内置的一些对象,不通过 BeanDefinition来创建,直接通过构造方法(new 一个)创建,因此没有配置元信息。通过 beanFactory.registerSingleton(); 进行注册,是Spring Bean对象,但是没有生命周期管理(我猜是应用停止时才会销毁,所以不需要进行管理了)
  • Resolvable Dependency:通过beanFactory.registerResolvableDependency(); 进行注册,不是 Spring Bean对象仅能依赖注入

Spring BeanDefinition 作为依赖来源

要素

  • 元数据:BeanDefinition
  • 注册:BeanDefinitionRegistry#registerBeanDefinition
  • 类型:延迟和非延迟
  • 顺序:Bean 生命周期顺序按照注册顺序

接口

BeanDefinition 的注册接口见org.springframework.beans.factory.support.BeanDefinitionRegistry,接口信息如下:

package org.springframework.beans.factory.support;

import org.springframework.beans.factory.BeanDefinitionStoreException;
import org.springframework.beans.factory.NoSuchBeanDefinitionException;
import org.springframework.beans.factory.config.BeanDefinition;
import org.springframework.core.AliasRegistry;

public interface BeanDefinitionRegistry extends AliasRegistry {

	// 注册 BeanDefinition
	void registerBeanDefinition(String beanName, BeanDefinition beanDefinition)
			throws BeanDefinitionStoreException;

	// 移除 BeanDefinition
	void removeBeanDefinition(String beanName) throws NoSuchBeanDefinitionException;

	// 获取 BeanDefinition
	BeanDefinition getBeanDefinition(String beanName) throws NoSuchBeanDefinitionException;

	// 判断是否包含 BeanDefinition
	boolean containsBeanDefinition(String beanName);

	// 获取 BeanDefinitionNames,记录了 BeanDefinition 的注册顺序
	String[] getBeanDefinitionNames();

	// 获取 BeanDefinition 的数量
	int getBeanDefinitionCount();

	/**
	 * Determine whether the given bean name is already in use within this registry,
	 * i.e. whether there is a local bean or alias registered under this name.
	 * @param beanName the name to check
	 * @return whether the given bean name is already in use
	 */
	boolean isBeanNameInUse(String beanName);

}

BeanDefinitionRegistry接口的实现类见 org.springframework.beans.factory.support.DefaultListableBeanFactory

单例对象作为依赖来源

要素

  • 来源:外部普通 Java 对象(不一定是 POJO)
  • 注册:SingletonBeanRegistry#registerSingleton

限制

  • 无生命周期管理
  • 无法实现延迟初始化 Bean

接口

单例对象的注册接口见org.springframework.beans.factory.config.SingletonBeanRegistry,接口信息如下:

package org.springframework.beans.factory.config;

import org.springframework.lang.Nullable;

public interface SingletonBeanRegistry {

   // 注册Bean
   void registerSingleton(String beanName, Object singletonObject);

   // 获取Bean
   @Nullable
   Object getSingleton(String beanName);

   // 判断是否包含
   boolean containsSingleton(String beanName);

   // 获取单例对象注册的名字,也是按照注册顺序
   String[] getSingletonNames();

   // 获取单例对象注册的数目
   int getSingletonCount();

   /**
    * Return the singleton mutex used by this registry (for external collaborators).
    * @return the mutex object (never {@code null})
    * @since 4.2
    */
   Object getSingletonMutex();

}

SingletonBeanRegistry 接口的实现类见org.springframework.beans.factory.support.DefaultSingletonBeanRegistry#registerSingleton

非 Spring 容器对象作为依赖来源

要素

  • 注册:ConfigurableListableBeanFactory#registerResolvableDependency

限制

  • 无生命周期管理
  • 无法实现延迟初始化 Bean
  • 无法通过依赖查找

接口

非 Spring 容器对象注册的接口见 org.springframework.beans.factory.config.ConfigurableListableBeanFactory,实现类为org.springframework.beans.factory.support.DefaultListableBeanFactory#registerResolvableDependency,代码如下:

@Override
	public void registerResolvableDependency(Class<?> dependencyType, @Nullable Object autowiredValue) {
		Assert.notNull(dependencyType, "Dependency type must not be null");
		if (autowiredValue != null) {
			if (!(autowiredValue instanceof ObjectFactory || dependencyType.isInstance(autowiredValue))) {
				throw new IllegalArgumentException("Value [" + autowiredValue +
						"] does not implement specified dependency type [" + dependencyType.getName() + "]");
			}
            /**
            将该对象加入 resolvableDependencies 中,key为类的类型,value是对象
            private final Map<Class<?>, Object> resolvableDependencies = new ConcurrentHashMap<>(16);
            **/
			this.resolvableDependencies.put(dependencyType, autowiredValue);
		}
	}

外部化配置作为依赖来源

要素

  • 类型:非常规 Spring 对象依赖来源

限制

  • 无生命周期管理
  • 无法实现延迟初始化 Bean
  • 无法通过依赖查找

接口

外部化配置的接口见org.springframework.beans.factory.config.AutowireCapableBeanFactory#resolveDependency,具体实现见

	// org.springframework.beans.factory.support.DefaultListableBeanFactory#resolveDependency
	@Override
	@Nullable
	public Object resolveDependency(DependencyDescriptor descriptor, @Nullable String requestingBeanName,
			@Nullable Set<String> autowiredBeanNames, @Nullable TypeConverter typeConverter) throws BeansException {

		descriptor.initParameterNameDiscovery(getParameterNameDiscoverer());
		if (Optional.class == descriptor.getDependencyType()) {
			return createOptionalDependency(descriptor, requestingBeanName);
		}
		else if (ObjectFactory.class == descriptor.getDependencyType() ||
				ObjectProvider.class == descriptor.getDependencyType()) {
			return new DependencyObjectProvider(descriptor, requestingBeanName);
		}
		else if (javaxInjectProviderClass == descriptor.getDependencyType()) {
			return new Jsr330Factory().createDependencyProvider(descriptor, requestingBeanName);
		}
		else {
			Object result = getAutowireCandidateResolver().getLazyResolutionProxyIfNecessary(
					descriptor, requestingBeanName);
			if (result == null) {
                // 处理外部化配置的注入
				result = doResolveDependency(descriptor, requestingBeanName, autowiredBeanNames, typeConverter);
			}
			return result;
		}
	}

有用的广告

​ 我是程序员,也热爱投资。个人认为,程序员这种职业(大部分是青春饭)非常适合投资,在年轻的积累本金,35岁后能过有睡后收入,想想就美滋滋。当然,如果没有专业的投资知识就是在股市中韭菜的份,这里推广下我学习投资知识的地方。简单说明下,这两个群都不会荐股,只是告诉你投资理念和知识,授人以鱼不如授人以渔,如果对投资感兴趣的人,我相信你会觉得相见恨晚。

老齐的读书圈:里面包含了几百本书籍,主要包括投资类,格局类,经营管理类三种。感兴趣的可以听听,三天内无条件可以退款。强烈推荐
在这里插入图片描述

齐俊杰的粉丝群:主要是对市场的解读,当然里面主要考虑的是周期的定位以及资产配置的相关知识。感兴趣的也可以进来听听,
在这里插入图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值