上篇文章说了,bean工厂后置处理器如何加载配置类
- public static void loadBeanDefinitions() {
- RootBeanDefinition rootBeanDefinitionA = new RootBeanDefinition(InstanceA.class);
- RootBeanDefinition rootBeanDefinitionB = new RootBeanDefinition(InstanceB.class);
- beanDefinitionMap.put("instanceA", rootBeanDefinitionA);
- beanDefinitionMap.put("instanceB", rootBeanDefinitionB);
- }
-
- @Component
- public class InstanceA {
- @Autowired
- private InstanceB instanceB;
-
- public InstanceB getInstanceB() {
- return instanceB;
- }
-
- public void setInstanceB(InstanceB instanceB) {
- this.instanceB = instanceB;
- }
-
- public InstanceA(InstanceB instanceB) {
- this.instanceB = instanceB;
- }
-
- public InstanceA() {
- System.out.println("实例化A");
- }
- }
首先把bean放入beanDefinition,之后,循环bean定义,通过bean的key来获取beanDefinition,
通过无参构造函数反射来获取class,再赋值属性。
- public static void main(String[] args) throws Exception {
- // 加载到beanDefinition
- loadBeanDefinitions();
-
- for (String key : beanDefinitionMap.keySet()) {
- // 先创建A
- getBean(key);
- }
- InstanceA instanceA = (InstanceA)getBean("instanceA");
- System.out.println(instanceA);
- }
-
- private static Map
singletonObjects = new ConcurrentHashMap<>(); -
- public static Object getBean(String beanName) throws Exception {
- Object singleton = getSingleton(beanName);
- if(singleton != null){
- return singleton;
- }
-
- // 实例化
- RootBeanDefinition rootBeanDefinition = (RootBeanDefinition) beanDefinitionMap.get(beanName);
- Class> beanClass = rootBeanDefinition.getBeanClass();
- // 通过class 无参构造函数 实例化
- Object instanceBean = beanClass.newInstance();
-
- singletonObjects.put(beanName, instanceBean);
- // 属性赋值
- Field[] declaredFields = beanClass.getDeclaredFields();
- for (Field declaredField : declaredFields) {
- Autowired annotation = declaredField.getAnnotation(Autowired.class);
- // 说明bean有autowired
- if (annotation != null) {
- // 打开访问权限
- declaredField.setAccessible(true);
- // byName byType 拿到了 instanceB名字
- String name = declaredField.getName();
- // 拿到B的bean
- Object fileObject = getBean(name);
- declaredField.set(instanceBean, fileObject);
- }
- }
- // 初始化
- // 放入缓存
- // singletonObjects.put(beanName, instanceBean);
- return instanceBean;
- }
-
- private static Object getSingleton(String beanName) {
- Object singleton = singletonObjects.get(beanName);
- if (singleton != null) {
- return singleton;
- }
- return null;
- }
这样写完之后,就不会有死循环,但是没有用到二级缓存,二级缓存可以用来放半成品的bean,解决多线程的情况下,多个线程同时创建bean,防止其他线程拿到不完整的bean,于是 加上二级缓存来写。
- private static Map<String, Object> singletonObjects = new ConcurrentHashMap<>();
- private static Map<String, Object> earlySingletonObjects = new ConcurrentHashMap<>();
-
- public static Object getBean(String beanName) throws Exception {
- Object singleton = getSingleton(beanName);
- if (singleton != null) {
- return singleton;
- }
-
- // 实例化
- RootBeanDefinition rootBeanDefinition = (RootBeanDefinition) beanDefinitionMap.get(beanName);
- Class<?> beanClass = rootBeanDefinition.getBeanClass();
- // 通过class 无参构造函数 实例化
- Object instanceBean = beanClass.newInstance();
-
- // 二级缓存
- earlySingletonObjects.put(beanName, instanceBean);
- // 属性赋值
- Field[] declaredFields = beanClass.getDeclaredFields();
- for (Field declaredField : declaredFields) {
- Autowired annotation = declaredField.getAnnotation(Autowired.class);
- // 说明bean有autowired
- if (annotation != null) {
- // 打开访问权限
- declaredField.setAccessible(true);
- // byName byType 拿到了 instanceB名字
- String name = declaredField.getName();
- // 拿到B的bean
- Object fileObject = getBean(name);
- declaredField.set(instanceBean, fileObject);
- }
- }
- // 初始化
- // 放入缓存
- singletonObjects.put(beanName, instanceBean);
- return instanceBean;
- }
-
- private static Object getSingleton(String beanName) {
- Object singleton = singletonObjects.get(beanName);
- if (singleton != null) {
- return singleton;
- }
- Object earlySingleton = earlySingletonObjects.get(beanName);
- if (earlySingleton != null) {
- return earlySingleton;
- }
- return null;
- }
用解耦的方式,beanPostProcessor来创建动态代理。
如果在最后调用动态代理,这时候循环依赖的bean就不是动态代理的bean,所以要在之前就创建动态代理。所以这里有两个地方调用动态代理,实例化之后和初始化之后调用。
只在循环依赖的情况下在实例化之后创建动态代理,所以需要判断当前是不是循环依赖。
前面一级缓存中没拿到,而二级缓存中有,才是循环依赖。
而spring源码里有一行代码,用来判断是否是循环依赖,加了一个正在创建对象的标识。
- private static Map
singletonObjects = new ConcurrentHashMap<>(); - private static Map
earlySingletonObjects = new ConcurrentHashMap<>(); - // 存放函数接口
- private static Map
singletonFactories = new ConcurrentHashMap<>(); -
- private static Set
singletonCurrennlyInCreation = new HashSet<>(); -
- public static Object getBean(String beanName) throws Exception {
- Object singleton = getSingleton(beanName);
- if (singleton != null) {
- return singleton;
- }
-
- // 正在创建
- if (!singletonCurrennlyInCreation.contains(beanName)) {
- singletonCurrennlyInCreation.add(beanName);
- }
-
- // 实例化
- RootBeanDefinition rootBeanDefinition = (RootBeanDefinition) beanDefinitionMap.get(beanName);
- Class> beanClass = rootBeanDefinition.getBeanClass();
- // 通过class 无参构造函数 实例化
- Object instanceBean = beanClass.newInstance();
-
- // 创建动态代理
- // 只在循环依赖的情况下在实例化之后创建动态代理
- //Object o = new JDKProxyBeanPostProcessor().getEarlyBeanReference(instanceBean,beanName);
- /*singletonFactories.put(beanName, new ObjectFactory() {
- @Override
- public Object getObject() throws BeansException {
- return new JDKProxyBeanPostProcessor().getEarlyBeanReference(instanceBean,beanName);
- }
- });*/
- singletonFactories.put(beanName, () -> new JDKProxyBeanPostProcessor().getEarlyBeanReference(instanceBean, beanName));
-
- // 二级缓存
- //earlySingletonObjects.put(beanName, instanceBean);
- // 属性赋值
- Field[] declaredFields = beanClass.getDeclaredFields();
- for (Field declaredField : declaredFields) {
- Autowired annotation = declaredField.getAnnotation(Autowired.class);
- // 说明bean有autowired
- if (annotation != null) {
- // 打开访问权限
- declaredField.setAccessible(true);
- // byName byType 拿到了 instanceB名字
- String name = declaredField.getName();
- // 拿到B的bean
- Object fileObject = getBean(name);
- declaredField.set(instanceBean, fileObject);
- }
- }
- // 初始化
-
-
- /*if(earlySingletonObjects.containsKey(beanName)){
- instanceBean = earlySingletonObjects.get(beanName);
- }*/
- // 放入缓存
- singletonObjects.put(beanName, instanceBean);
- return instanceBean;
- }
-
- private static Object getSingleton(String beanName) {
- /* Object singleton = singletonObjects.get(beanName);
- if (singleton != null) {
- return singleton;
- }
- Object earlySingleton = earlySingletonObjects.get(beanName);
- if (earlySingleton != null) {
- return earlySingleton;
- }
- return null;*/
- Object bean = singletonObjects.get(beanName);
- if (bean == null && singletonCurrennlyInCreation.contains(beanName)) {
- // 是循环依赖
- bean = earlySingletonObjects.get(beanName);
- synchronized (singletonObjects){
- if(bean == null){
- ObjectFactory objectFactory = singletonFactories.get(beanName);
- if (objectFactory != null) {
- // 钩子函数 去创建 aop代理
- bean = objectFactory.getObject();
- earlySingletonObjects.put(beanName, bean);
- singletonFactories.remove(beanName);
- }
- return bean;
- }
- }
- }
- return bean;
- }