spring 核心原理解析

spring 核心原理解析,第1张

spring 核心原理解析

以AnnotationConfigApplicationContext举例

AnnotationConfigApplicationContext context = new AnnotationConfigApplicationContext(AppConfig.class);
UserService userService = (UserService) context.getBean("userService");
userService.test();

1:创建一个上下文对象

2:获取一个bean;

3:执行方法

AppConfig中的内容为:

@ComponentScan("com.zhouyu")
public class AppConfig {

	@Bean
	public UserService userService(){
		return new UserService();
	}

}

问题:为啥getbean("userService")可以拿到一个userService对象呢

需要关注的肯定就是new AnnotationConfigApplicationContext(Appconfig.class)和getbean里做了啥。也就是我们关注的spring帮我们做了啥。

在调用AnnotationConfigApplicationContext的构造函数时,spring确实帮我们做了以下工作,以下流程只是截取了一个分支的一小段逻辑,大致的一个流程

1:解析AppConfig配置类,得到扫描路径

2:遍历扫描路径下的所有的java类,如果发现某个类或者父注解上有@component注解,spring会将此类记录下来。存到一个Map中,就是所谓的beanDefinitionMap

3:Spring会根据某个规则生成当前类对应的beanName,作为key存入Map,当前类作为value

4:beanDefinition中的name会注册到一个list中,遍历list,拿到Class对象,反射生成对象,放入单例池

然后调用context.getbean("userService"),从单例池中拿到对应的实例,执行test方法。

spring具体如果创建一个bean呢,大致如下

1:利用该类的构造函数来实例化得到一个对象,如类中存在多个构造函数,spring会进行选择,这个叫做推断构造方法,如下

(1):如果一个类中只有一个构造方法。无论是无参或者有参,spring都会采用这个构造方法

(2):如果多个构造方法,分情况

           i:多个构造方法中存在一个无参构造方法,采用无参构造方法

           ii:多个构造方法且无构造方法,spring会报错

           iii:多个构造方法,有构造方法用Autowired修饰,spring采用此方法。

如果构造方法中存在参数的引用,spring会getbean入参

2:得到一个对象后,spring会对对象中@Autowired的属性进行依赖注入,依赖注入是在实例化后通过beanpostprocessor实现的

3:依赖注入以后,spring会判断该类是否实现了BeanNameAware接口,BeanClassLoaderAware接口、BeanFactoryAware接口,如果实现了,就表示当前对象必须实现该接口中所定义的setBeanName()、setBeanClassLoader()、setBeanFactory()方法,那Spring就会调用这些方法并传入相应的参数(Aware回调)

4:Aware回调后,Spring会判断对象中是否某个方法被@PostContruct注解修饰,如果存在,spring会调用次方法(初始化前)

5:Spring会判断对象是否实现了InitialzingBean接口,如果实现了,spring会调用该类中的afterPropertiesSet方法(初始化)

6:最后,Spring会判断当前对象需不需要进行AOP,如果不需要那么Bean就创建完了,如果需要进行AOP,则会进行动态代理并生成一个代理对象做为Bean(初始化后)

总结BeanPostProcessor
    InstantiationAwareBeanPostProcessor.postProcessBeforeInstantiation()实例化MergedBeanDefinitionPostProcessor.postProcessMergedBeanDefinition()InstantiationAwareBeanPostProcessor.postProcessAfterInstantiation()自动注入InstantiationAwareBeanPostProcessor.postProcessProperties()Aware对象BeanPostProcessor.postProcessBeforeInitialization()初始化BeanPostProcessor.postProcessAfterInitialization()

大致的流程就是这样,写这些东西只是为了对自己学习的东西做一些总结,加深下映像,有可能有东西是表达错误或者很多东西没写到的,勿喷。

欢迎分享,转载请注明来源:内存溢出

原文地址: http://outofmemory.cn/zaji/5703416.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2022-12-17
下一篇 2022-12-17

发表评论

登录后才能评论

评论列表(0条)

保存