spring源码阅读(3)-- 容器启动之BeanFactoryPostProcessor
接著上文《spring源碼閱讀(2)-- 容器啟動之加載BeanDefinition》,當spring加載完所有BeanDefinition時,并不會馬上去創建bean,而是先配置beanFactory,例如設置一下裝配規則和判斷是否需要創建一些指定的bean。
1 protected void prepareBeanFactory(ConfigurableListableBeanFactory beanFactory) { 2 // Tell the internal bean factory to use the context's class loader etc. 3 beanFactory.setBeanClassLoader(getClassLoader()); 4 beanFactory.setBeanExpressionResolver(new StandardBeanExpressionResolver(beanFactory.getBeanClassLoader())); 5 beanFactory.addPropertyEditorRegistrar(new ResourceEditorRegistrar(this, getEnvironment())); 6 7 // Configure the bean factory with context callbacks. 8 //添加ApplicationContextAwareProcessor用于處理實現了EnvironmentAware、EmbeddedValueResolverAware、ApplicationContextAware接口的bean 9 beanFactory.addBeanPostProcessor(new ApplicationContextAwareProcessor(this)); 10 //忽略以下bean的依賴注入 11 beanFactory.ignoreDependencyInterface(ResourceLoaderAware.class); 12 beanFactory.ignoreDependencyInterface(ApplicationEventPublisherAware.class); 13 beanFactory.ignoreDependencyInterface(MessageSourceAware.class); 14 beanFactory.ignoreDependencyInterface(ApplicationContextAware.class); 15 beanFactory.ignoreDependencyInterface(EnvironmentAware.class); 16 17 // BeanFactory interface not registered as resolvable type in a plain factory. 18 // MessageSource registered (and found for autowiring) as a bean. 19 //注冊自動裝配模式下的特殊依賴,例如被注入的是BeanFactory類型,那么注入的就是beanFactory 20 beanFactory.registerResolvableDependency(BeanFactory.class, beanFactory); 21 beanFactory.registerResolvableDependency(ResourceLoader.class, this); 22 beanFactory.registerResolvableDependency(ApplicationEventPublisher.class, this); 23 beanFactory.registerResolvableDependency(ApplicationContext.class, this); 24 25 // Detect a LoadTimeWeaver and prepare for weaving, if found. 26 if (beanFactory.containsBean(LOAD_TIME_WEAVER_BEAN_NAME)) { 27 beanFactory.addBeanPostProcessor(new LoadTimeWeaverAwareProcessor(beanFactory)); 28 // Set a temporary ClassLoader for type matching. 29 beanFactory.setTempClassLoader(new ContextTypeMatchClassLoader(beanFactory.getBeanClassLoader())); 30 } 31 32 // Register default environment beans. 33 if (!beanFactory.containsLocalBean(ENVIRONMENT_BEAN_NAME)) { 34 beanFactory.registerSingleton(ENVIRONMENT_BEAN_NAME, getEnvironment()); 35 } 36 if (!beanFactory.containsLocalBean(SYSTEM_PROPERTIES_BEAN_NAME)) { 37 beanFactory.registerSingleton(SYSTEM_PROPERTIES_BEAN_NAME, getEnvironment().getSystemProperties()); 38 } 39 if (!beanFactory.containsLocalBean(SYSTEM_ENVIRONMENT_BEAN_NAME)) { 40 beanFactory.registerSingleton(SYSTEM_ENVIRONMENT_BEAN_NAME, getEnvironment().getSystemEnvironment()); 41 } 42 }當設置完beanFactory,接下來就是執行BeanFactoryPostProcessor。BeanFactoryPostProcessor是spring容器啟動時暴露給用戶的一個擴展點,允許用戶在spring創建bean之前做修改或動態添加bean,動態注冊bean可以使用BeanFactoryPostProcessor的子類BeanDefinitionRegistryPostProcessor。BeanFactoryPostProcessor接口定義如下:
1 public interface BeanFactoryPostProcessor { 2 3 void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) throws BeansException; 4 5 }當我們實現了BeanFactoryPostProcessor,spring是怎么去執行的呢?
spring容器在執行刷新時,當加載完BeanDefinition和配置好beanFactory時,會進入AbstractApplicationContext.invokeBeanFactoryPostProcessors,方法里首先調用PostProcessorRegistrationDelegate.invokeBeanFactoryPostProcessors去執行實現了BeanFactoryPostProcessor的postProcessBeanFactory方法,然后再判斷是否新添加了loadTimeWeaver這個bean,如果有,添加LoadTimeWeaverAwareProcessor
1 protected void invokeBeanFactoryPostProcessors(ConfigurableListableBeanFactory beanFactory) { 2 PostProcessorRegistrationDelegate.invokeBeanFactoryPostProcessors(beanFactory, getBeanFactoryPostProcessors()); 3 4 // Detect a LoadTimeWeaver and prepare for weaving, if found in the meantime 5 // (e.g. through an @Bean method registered by ConfigurationClassPostProcessor) 6 if (beanFactory.getTempClassLoader() == null && beanFactory.containsBean(LOAD_TIME_WEAVER_BEAN_NAME)) { 7 beanFactory.addBeanPostProcessor(new LoadTimeWeaverAwareProcessor(beanFactory)); 8 beanFactory.setTempClassLoader(new ContextTypeMatchClassLoader(beanFactory.getBeanClassLoader())); 9 } 10 }?
進入PostProcessorRegistrationDelegate.invokeBeanFactoryPostProcessors方法,方法里首先判斷beanFactory是不是一個bean注冊中心,如果是,循環遍歷傳入的BeanFactoryPostProcessor,判斷是否是BeanDefinitionRegistryPostProcessor的實現,如果是,執行BeanDefinitionRegistryPostProcessor.postProcessBeanDefinitionRegistry,然后保存到一個集合用于在執行完所有的BeanDefinitionRegistryPostProcessor.postProcessBeanDefinitionRegistry方法之后,再執行BeanFactoryPostProcessor.postProcessBeanFactory。
1 public static void invokeBeanFactoryPostProcessors( 2 ConfigurableListableBeanFactory beanFactory, List<BeanFactoryPostProcessor> beanFactoryPostProcessors) { 3 4 // Invoke BeanDefinitionRegistryPostProcessors first, if any. 5 Set<String> processedBeans = new HashSet<String>(); 6 7 if (beanFactory instanceof BeanDefinitionRegistry) { 8 BeanDefinitionRegistry registry = (BeanDefinitionRegistry) beanFactory; 9 List<BeanFactoryPostProcessor> regularPostProcessors = new LinkedList<BeanFactoryPostProcessor>(); 10 List<BeanDefinitionRegistryPostProcessor> registryPostProcessors = 11 new LinkedList<BeanDefinitionRegistryPostProcessor>(); 12 13 for (BeanFactoryPostProcessor postProcessor : beanFactoryPostProcessors) { 14 if (postProcessor instanceof BeanDefinitionRegistryPostProcessor) { 15 BeanDefinitionRegistryPostProcessor registryPostProcessor = 16 (BeanDefinitionRegistryPostProcessor) postProcessor; 17 registryPostProcessor.postProcessBeanDefinitionRegistry(registry); 18 registryPostProcessors.add(registryPostProcessor); 19 } 20 else { 21 regularPostProcessors.add(postProcessor); 22 } 23 } 24 25 // Do not initialize FactoryBeans here: We need to leave all regular beans 26 // uninitialized to let the bean factory post-processors apply to them! 27 // Separate between BeanDefinitionRegistryPostProcessors that implement 28 // PriorityOrdered, Ordered, and the rest. 29 String[] postProcessorNames = 30 beanFactory.getBeanNamesForType(BeanDefinitionRegistryPostProcessor.class, true, false); 31 32 // First, invoke the BeanDefinitionRegistryPostProcessors that implement PriorityOrdered. 33 List<BeanDefinitionRegistryPostProcessor> priorityOrderedPostProcessors = new ArrayList<BeanDefinitionRegistryPostProcessor>(); 34 for (String ppName : postProcessorNames) { 35 if (beanFactory.isTypeMatch(ppName, PriorityOrdered.class)) { 36 priorityOrderedPostProcessors.add(beanFactory.getBean(ppName, BeanDefinitionRegistryPostProcessor.class)); 37 processedBeans.add(ppName); 38 } 39 } 40 sortPostProcessors(beanFactory, priorityOrderedPostProcessors); 41 registryPostProcessors.addAll(priorityOrderedPostProcessors); 42 invokeBeanDefinitionRegistryPostProcessors(priorityOrderedPostProcessors, registry); 43 44 // Next, invoke the BeanDefinitionRegistryPostProcessors that implement Ordered. 45 postProcessorNames = beanFactory.getBeanNamesForType(BeanDefinitionRegistryPostProcessor.class, true, false); 46 List<BeanDefinitionRegistryPostProcessor> orderedPostProcessors = new ArrayList<BeanDefinitionRegistryPostProcessor>(); 47 for (String ppName : postProcessorNames) { 48 if (!processedBeans.contains(ppName) && beanFactory.isTypeMatch(ppName, Ordered.class)) { 49 orderedPostProcessors.add(beanFactory.getBean(ppName, BeanDefinitionRegistryPostProcessor.class)); 50 processedBeans.add(ppName); 51 } 52 } 53 sortPostProcessors(beanFactory, orderedPostProcessors); 54 registryPostProcessors.addAll(orderedPostProcessors); 55 invokeBeanDefinitionRegistryPostProcessors(orderedPostProcessors, registry); 56 57 // Finally, invoke all other BeanDefinitionRegistryPostProcessors until no further ones appear. 58 boolean reiterate = true; 59 while (reiterate) { 60 reiterate = false; 61 postProcessorNames = beanFactory.getBeanNamesForType(BeanDefinitionRegistryPostProcessor.class, true, false); 62 for (String ppName : postProcessorNames) { 63 if (!processedBeans.contains(ppName)) { 64 BeanDefinitionRegistryPostProcessor pp = beanFactory.getBean(ppName, BeanDefinitionRegistryPostProcessor.class); 65 registryPostProcessors.add(pp); 66 processedBeans.add(ppName); 67 pp.postProcessBeanDefinitionRegistry(registry); 68 reiterate = true; 69 } 70 } 71 } 72 73 // Now, invoke the postProcessBeanFactory callback of all processors handled so far. 74 invokeBeanFactoryPostProcessors(registryPostProcessors, beanFactory); 75 invokeBeanFactoryPostProcessors(regularPostProcessors, beanFactory); 76 } 77 78 else { 79 // Invoke factory processors registered with the context instance. 80 invokeBeanFactoryPostProcessors(beanFactoryPostProcessors, beanFactory); 81 } 82 83 // Do not initialize FactoryBeans here: We need to leave all regular beans 84 // uninitialized to let the bean factory post-processors apply to them! 85 String[] postProcessorNames = 86 beanFactory.getBeanNamesForType(BeanFactoryPostProcessor.class, true, false); 87 88 // Separate between BeanFactoryPostProcessors that implement PriorityOrdered, 89 // Ordered, and the rest. 90 List<BeanFactoryPostProcessor> priorityOrderedPostProcessors = new ArrayList<BeanFactoryPostProcessor>(); 91 List<String> orderedPostProcessorNames = new ArrayList<String>(); 92 List<String> nonOrderedPostProcessorNames = new ArrayList<String>(); 93 for (String ppName : postProcessorNames) { 94 if (processedBeans.contains(ppName)) { 95 // skip - already processed in first phase above 96 } 97 else if (beanFactory.isTypeMatch(ppName, PriorityOrdered.class)) { 98 priorityOrderedPostProcessors.add(beanFactory.getBean(ppName, BeanFactoryPostProcessor.class)); 99 } 100 else if (beanFactory.isTypeMatch(ppName, Ordered.class)) { 101 orderedPostProcessorNames.add(ppName); 102 } 103 else { 104 nonOrderedPostProcessorNames.add(ppName); 105 } 106 } 107 108 // First, invoke the BeanFactoryPostProcessors that implement PriorityOrdered. 109 sortPostProcessors(beanFactory, priorityOrderedPostProcessors); 110 invokeBeanFactoryPostProcessors(priorityOrderedPostProcessors, beanFactory); 111 112 // Next, invoke the BeanFactoryPostProcessors that implement Ordered. 113 List<BeanFactoryPostProcessor> orderedPostProcessors = new ArrayList<BeanFactoryPostProcessor>(); 114 for (String postProcessorName : orderedPostProcessorNames) { 115 orderedPostProcessors.add(beanFactory.getBean(postProcessorName, BeanFactoryPostProcessor.class)); 116 } 117 sortPostProcessors(beanFactory, orderedPostProcessors); 118 invokeBeanFactoryPostProcessors(orderedPostProcessors, beanFactory); 119 120 // Finally, invoke all other BeanFactoryPostProcessors. 121 List<BeanFactoryPostProcessor> nonOrderedPostProcessors = new ArrayList<BeanFactoryPostProcessor>(); 122 for (String postProcessorName : nonOrderedPostProcessorNames) { 123 nonOrderedPostProcessors.add(beanFactory.getBean(postProcessorName, BeanFactoryPostProcessor.class)); 124 } 125 invokeBeanFactoryPostProcessors(nonOrderedPostProcessors, beanFactory); 126 127 // Clear cached merged bean definitions since the post-processors might have 128 // modified the original metadata, e.g. replacing placeholders in values... 129 beanFactory.clearMetadataCache(); 130 }invokeBeanFactoryPostProcessors方法里會找出所有的bean,先排序然后再執行相應的方法。從源碼可以看得出,先執行的是傳進來的BeanFactoryPostProcessor,第二是實現了PriorityOrdered的接口,第三是實現了Ordered接口,最后的就是沒有指定順序的,而實現了BeanDefinitionRegistryPostProcessor的,會先執行BeanDefinitionRegistryPostProcessor.postProcessBeanDefinitionRegistry。
至此,spring對BeanFactoryPostProcessor的擴展點已處理完,從源碼可以開出,BeanFactoryPostProcessor的處理會觸發bean的創建。
轉載于:https://www.cnblogs.com/hanjiehu/p/8671300.html
總結
以上是生活随笔為你收集整理的spring源码阅读(3)-- 容器启动之BeanFactoryPostProcessor的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 高速缓冲存储器(Cache)
- 下一篇: 安全攻防全景图