成人午夜视频全免费观看高清-秋霞福利视频一区二区三区-国产精品久久久久电影小说-亚洲不卡区三一区三区一区

關(guān)于Spring啟動(dòng)時(shí)Context加載源碼分析

前言

目前創(chuàng)新互聯(lián)建站已為近1000家的企業(yè)提供了網(wǎng)站建設(shè)、域名、虛擬主機(jī)、成都網(wǎng)站托管、企業(yè)網(wǎng)站設(shè)計(jì)、滎陽(yáng)網(wǎng)站維護(hù)等服務(wù),公司將堅(jiān)持客戶(hù)導(dǎo)向、應(yīng)用為本的策略,正道將秉承"和諧、參與、激情"的文化,與客戶(hù)和合作伙伴齊心協(xié)力一起成長(zhǎng),共同發(fā)展。

本文主要給大家介紹了關(guān)于Spring啟動(dòng)時(shí)Context加載的相關(guān)內(nèi)容,分享出來(lái)供大家參考學(xué)習(xí),下面話不多說(shuō)了,來(lái)一起看看詳細(xì)的介紹吧。

測(cè)試源碼下載test-annotation.zip

有如下的代碼

@Component
public class HelloWorldService {
 @Value("${name:World}")
 private String name;
 public String getHelloMessage() {
 return "Hello " + this.name;
 }
}

@Configuration
public class BootStrap {
 @Bean
 public static HelloWorldService helloService() {
 return new HelloWorldService();
 }
 public static void main(String[] args) {
 InstantiationStrategy instantiationStrategy = new SimpleInstantiationStrategy();
 DefaultListableBeanFactory beanFactory = new DefaultListableBeanFactory();
 beanFactory.setInstantiationStrategy(instantiationStrategy);
 AnnotationConfigApplicationContext applicationContext = 
 new AnnotationConfigApplicationContext(beanFactory);
 applicationContext.register(BootStrap.class);
 applicationContext.refresh();
 HelloWorldService service = applicationContext.getBean(HelloWorldService.class);
 System.out.println(service.getHelloMessage());
 applicationContext.close();
 }
}

HelloWorldService.getHelloMessage方法簡(jiǎn)單的返回name的值, BootStrap.main方法中使用AnnotationConfigApplicationContext 構(gòu)造一個(gè)上下文對(duì)象, 為了演示的方便, 顯示的聲明了DefaultListableBeanFactory和InstantiationStrategy實(shí)例。通過(guò)applicationContext.getBean()獲取bean的引用,并調(diào)用 service.getHelloMessage() 方法。

上下文的加載主要發(fā)生在applicationContext.register方法和applicationContext.refresh方法中,
applicationContext.register方法的作用是為參數(shù)(使用@Configuration注解的class)生成BeanDefinition 對(duì)象并調(diào)用DefaultListableBeanFactory.registerBeanDefinition將BeanDefinition注冊(cè)到DefaultListableBeanFactory中。

applicationContext.refresh()的功能要更多,主要功能一的是調(diào)用PostProcessor為@Configuration類(lèi)中的@Bean標(biāo)注的方法生成對(duì)應(yīng)的BeanDefinition對(duì)象,并注冊(cè)到DefaultListableBeanFactory中,功能二是遍歷DefaultListableBeanFactory中BeanDefinition, 產(chǎn)生真正的對(duì)象。

為@Configuration類(lèi)中@Bean標(biāo)注的方法生成BeanDefinition對(duì)象詳細(xì)過(guò)程如下

步驟1、找到合適的BeanDefinitionRegistryPostProcessor處理器

org.springframework.context.support.PostProcessorRegistrationDelegate.invokeBeanFactoryPostProcessors() {
 ...
 //獲取適用的BeanDefinitionRegistryPostProcessor bean名稱(chēng)
 String[] postProcessorNames =
  beanFactory.getBeanNamesForType(BeanDefinitionRegistryPostProcessor.class, true, false);
 ...
 //根據(jù)beanName獲取PostProcessor, 處理@Configuration標(biāo)注類(lèi)的beanName為
 //org.springframework.context.annotation.internalConfigurationAnnotationProcessor 
 //實(shí)現(xiàn)為org.springframework.context.annotation.ConfigurationClassPostProcessor
 ConfigurationClassPostProcessor postProcessor =beanFactory.getBean(postProcessorNames[0], BeanDefinitionRegistryPostProcessor.class)
}

步驟2、為@Configuration產(chǎn)生ConfigurationClass對(duì)象

//使用ConfigurationClassParser解析@Configuration標(biāo)注的類(lèi),

//每一個(gè)@Configuration標(biāo)注的類(lèi)產(chǎn)生一個(gè)ConfigurationClass對(duì)象,

//ConfigurationClass.getBeanMethods()能獲得該類(lèi)中所有使用@Bean標(biāo)注的方法,

//@Bean標(biāo)注的方法使用BeanMethod對(duì)象表示

org.springframework.context.annotation.ConfigurationClassPostProcessor.processConfigBeanDefinitions(BeanDefinitionRegistry registry) {
 ConfigurationClassParser parser = new ConfigurationClassParser(
 this.metadataReaderFactory, this.problemReporter, this.environment,
 this.resourceLoader, this.componentScanBeanNameGenerator, registry);
 parser.parse(configCandidates);
 parser.validate();
 this.reader.loadBeanDefinitions(parser.getConfigurationClasses());
}

步驟3、@Bean標(biāo)注的方法產(chǎn)生BeanDefinition并注入到DefaultListableBeanFactory中

org.springframework.context.annotation.ConfigurationClassBeanDefinitionReader.loadBeanDefinitionsForBeanMethod(BeanMethod beanMethod) {
 ConfigurationClassBeanDefinition beanDef = new ConfigurationClassBeanDefinition(configClass);
 beanDef.setBeanClassName(configClass.getMetadata().getClassName());
 beanDef.setFactoryMethodName(metadata.getMethodName());
 //registry 是DefaultListableBeanFactory的實(shí)例
 this.registry.registerBeanDefinition(beanName, beanDefToRegister);
}

此過(guò)程的調(diào)用棧:

關(guān)于Spring啟動(dòng)時(shí)Context加載源碼分析

根據(jù)BeanDefinition生成實(shí)例過(guò)程的調(diào)用棧:

關(guān)于Spring啟動(dòng)時(shí)Context加載源碼分析

總結(jié)

以上就是這篇文章的全部?jī)?nèi)容了,希望本文的內(nèi)容對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,如果有疑問(wèn)大家可以留言交流,謝謝大家對(duì)創(chuàng)新互聯(lián)的支持。

網(wǎng)站標(biāo)題:關(guān)于Spring啟動(dòng)時(shí)Context加載源碼分析
當(dāng)前網(wǎng)址:http://jinyejixie.com/article18/iejjgp.html

成都網(wǎng)站建設(shè)公司_創(chuàng)新互聯(lián),為您提供網(wǎng)站維護(hù)、品牌網(wǎng)站制作、網(wǎng)站營(yíng)銷(xiāo)關(guān)鍵詞優(yōu)化、企業(yè)網(wǎng)站制作、企業(yè)建站

廣告

聲明:本網(wǎng)站發(fā)布的內(nèi)容(圖片、視頻和文字)以用戶(hù)投稿、用戶(hù)轉(zhuǎn)載內(nèi)容為主,如果涉及侵權(quán)請(qǐng)盡快告知,我們將會(huì)在第一時(shí)間刪除。文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如需處理請(qǐng)聯(lián)系客服。電話:028-86922220;郵箱:631063699@qq.com。內(nèi)容未經(jīng)允許不得轉(zhuǎn)載,或轉(zhuǎn)載時(shí)需注明來(lái)源: 創(chuàng)新互聯(lián)

h5響應(yīng)式網(wǎng)站建設(shè)
永仁县| 固镇县| 庆元县| 阿拉善盟| 黑山县| 泾源县| 哈尔滨市| 察隅县| 永宁县| 五寨县| 兴安盟| 平顺县| 阿巴嘎旗| 荥阳市| 博爱县| 芦山县| 临武县| 富阳市| 苗栗县| 平武县| 威海市| 岱山县| 巴青县| 绥滨县| 江油市| 南投县| 江源县| 临澧县| 文安县| 黄山市| 嘉鱼县| 海口市| 江城| 杭锦后旗| 卫辉市| 黄梅县| 镇雄县| 澄江县| 宜宾市| 华蓥市| 登封市|