最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

Spring實現(xiàn)默認(rèn)標(biāo)簽解析流程

 更新時間:2022年01月16日 11:55:14   作者:大大明001  
這篇文章主要為大家詳細(xì)介紹了Spring實現(xiàn)默認(rèn)標(biāo)簽解析流程,文中示例代碼介紹的非常詳細(xì),具有一定的參考價值,感興趣的小伙伴們可以參考一下

本文實例為大家分享了Spring實現(xiàn)默認(rèn)標(biāo)簽解析流程的具體代碼,供大家參考,具體內(nèi)容如下

承接上文,進(jìn)入parseBeanDefinitions()方法

protected void parseBeanDefinitions(Element root, BeanDefinitionParserDelegate delegate) {
?? ??? ?if (delegate.isDefaultNamespace(root)) {
?? ??? ??? ?NodeList nl = root.getChildNodes();
?? ??? ??? ?for (int i = 0; i < nl.getLength(); i++) {
?? ??? ??? ??? ?Node node = nl.item(i);
?? ??? ??? ??? ?if (node instanceof Element) {
?? ??? ??? ??? ??? ?Element ele = (Element) node;
?? ??? ??? ??? ??? ?if (delegate.isDefaultNamespace(ele)) {
?? ??? ??? ??? ??? ??? ?//默認(rèn)標(biāo)簽解析,此次著重分析這個方法
?? ??? ??? ??? ??? ??? ?parseDefaultElement(ele, delegate);
?? ??? ??? ??? ??? ?}
?? ??? ??? ??? ??? ?else {
?? ??? ??? ??? ??? ??? ?//自定義標(biāo)簽解析
?? ??? ??? ??? ??? ??? ?delegate.parseCustomElement(ele);
?? ??? ??? ??? ??? ?}
?? ??? ??? ??? ?}
?? ??? ??? ?}
?? ??? ?}
?? ??? ?else {
?? ??? ??? ?delegate.parseCustomElement(root);
?? ??? ?}
?? ?}

-進(jìn)入parseDefaultElement()方法,此方法在parseBeanDefinitions的下方

private void parseDefaultElement(Element ele, BeanDefinitionParserDelegate delegate) {
?? ??? ?//import標(biāo)簽解析 ,可看可不看
?? ??? ?if (delegate.nodeNameEquals(ele, IMPORT_ELEMENT)) {
?? ??? ??? ?importBeanDefinitionResource(ele);
?? ??? ?}
?? ??? ?//alias標(biāo)簽解析 別名標(biāo)簽 可看可不看
?? ??? ?else if (delegate.nodeNameEquals(ele, ALIAS_ELEMENT)) {
?? ??? ??? ?processAliasRegistration(ele);
?? ??? ?}
?? ??? ?//bean標(biāo)簽,重要(看這個方法)
?? ??? ?else if (delegate.nodeNameEquals(ele, BEAN_ELEMENT)) {
?? ??? ??? ?processBeanDefinition(ele, delegate);
?? ??? ?}
?? ??? ?//beans標(biāo)簽,不重要
?? ??? ?else if (delegate.nodeNameEquals(ele, NESTED_BEANS_ELEMENT)) {
?? ??? ??? ?// recurse
?? ??? ??? ?doRegisterBeanDefinitions(ele);
?? ??? ?}
?? ?}

-進(jìn)入到bean標(biāo)簽解析方法

protected void processBeanDefinition(Element ele, BeanDefinitionParserDelegate delegate) {
?? ??? ?//重點看這個方法 ,解析document,封裝成BeanDefinition
?? ??? ?BeanDefinitionHolder bdHolder = delegate.parseBeanDefinitionElement(ele);
?? ??? ?if (bdHolder != null) {
?? ??? ??? ?bdHolder = delegate.decorateBeanDefinitionIfRequired(ele, bdHolder);
?? ??? ??? ?try {
?? ??? ??? ??? ?//完成document到BeanDefinition對象轉(zhuǎn)換后,對BeanDefinition對象進(jìn)行緩存注冊
?? ??? ??? ??? ?// Register the final decorated instance.
?? ??? ??? ??? ?BeanDefinitionReaderUtils.registerBeanDefinition(bdHolder, getReaderContext().getRegistry());
?? ??? ??? ?}
?? ??? ??? ?catch (BeanDefinitionStoreException ex) {
?? ??? ??? ??? ?getReaderContext().error("Failed to register bean definition with name '" +
?? ??? ??? ??? ??? ??? ?bdHolder.getBeanName() + "'", ele, ex);
?? ??? ??? ?}
?? ??? ??? ?// Send registration event.
?? ??? ??? ?getReaderContext().fireComponentRegistered(new BeanComponentDefinition(bdHolder));
?? ??? ?}
?? ?}

進(jìn)入

public BeanDefinitionHolder parseBeanDefinitionElement(Element ele) {
?? ??? ?//思考一下這個的第二個參數(shù)為啥要傳入null(BeanDefinition類型),進(jìn)入方法
?? ??? ?return parseBeanDefinitionElement(ele, null);
?? ?}

打開parseBeanDefinitionElement方法

public BeanDefinitionHolder parseBeanDefinitionElement(Element ele, @Nullable BeanDefinition containingBean) {
?? ??? ?//獲取id
?? ??? ?String id = ele.getAttribute(ID_ATTRIBUTE);
?? ??? ?//獲取別名
?? ??? ?String nameAttr = ele.getAttribute(NAME_ATTRIBUTE);
?? ??? ?//將別名添加到aliases內(nèi)
?? ??? ?List<String> aliases = new ArrayList<>();
?? ??? ?if (StringUtils.hasLength(nameAttr)) {
?? ??? ??? ?String[] nameArr = StringUtils.tokenizeToStringArray(nameAttr, MULTI_VALUE_ATTRIBUTE_DELIMITERS);
?? ??? ??? ?aliases.addAll(Arrays.asList(nameArr));
?? ??? ?}

?? ??? ?String beanName = id;
?? ??? ?if (!StringUtils.hasText(beanName) && !aliases.isEmpty()) {
?? ??? ??? ?beanName = aliases.remove(0);
?? ??? ??? ?if (logger.isTraceEnabled()) {
?? ??? ??? ??? ?logger.trace("No XML 'id' specified - using '" + beanName +
?? ??? ??? ??? ??? ??? ?"' as bean name and " + aliases + " as aliases");
?? ??? ??? ?}
?? ??? ?}

?? ??? ?//檢查beanName是否重復(fù)
?? ??? ?if (containingBean == null) {
?? ??? ??? ?checkNameUniqueness(beanName, aliases, ele);
?? ??? ?}

?? ??? ?//<bean>標(biāo)簽解析的核心方法
?? ??? ?AbstractBeanDefinition beanDefinition = parseBeanDefinitionElement(ele, beanName, containingBean);
?? ??? ?if (beanDefinition != null) {
?? ??? ??? ?......不重要的就不要看了,浪費時間
?? ??? ?}

?? ??? ?return null;
?? ?}

看核心方法parseBeanDefinitionElement

public AbstractBeanDefinition parseBeanDefinitionElement(
?? ??? ??? ?Element ele, String beanName, @Nullable BeanDefinition containingBean) {

?? ??? ?this.parseState.push(new BeanEntry(beanName));

?? ??? ?String className = null;
?? ??? ?if (ele.hasAttribute(CLASS_ATTRIBUTE)) {
?? ??? ??? ?className = ele.getAttribute(CLASS_ATTRIBUTE).trim();
?? ??? ?}
?? ??? ?String parent = null;
?? ??? ?if (ele.hasAttribute(PARENT_ATTRIBUTE)) {
?? ??? ??? ?parent = ele.getAttribute(PARENT_ATTRIBUTE);
?? ??? ?}

?? ??? ?try {
?? ??? ??? ?//創(chuàng)建GenericBeanDefinition對象
?? ??? ??? ?AbstractBeanDefinition bd = createBeanDefinition(className, parent);

?? ??? ??? ?//解析bean標(biāo)簽的屬性,并把解析出來的屬性設(shè)置到BeanDefinition對象中
?? ??? ??? ?parseBeanDefinitionAttributes(ele, beanName, containingBean, bd);
?? ??? ??? ?bd.setDescription(DomUtils.getChildElementValueByTagName(ele, DESCRIPTION_ELEMENT));

?? ??? ??? ?//解析bean中的meta標(biāo)簽
?? ??? ??? ?parseMetaElements(ele, bd);
?? ??? ??? ?//解析bean中的lookup-method標(biāo)簽 ?,可看可不看
?? ??? ??? ?parseLookupOverrideSubElements(ele, bd.getMethodOverrides());
?? ??? ??? ?//解析bean中的replaced-method標(biāo)簽 ?,可看可不看
?? ??? ??? ?parseReplacedMethodSubElements(ele, bd.getMethodOverrides());

?? ??? ??? ?//解析bean中的constructor-arg標(biāo)簽 ,可看可不看
?? ??? ??? ?parseConstructorArgElements(ele, bd);
?? ??? ??? ?//解析bean中的property標(biāo)簽 可看可不看
?? ??? ??? ?parsePropertyElements(ele, bd);
?? ??? ??? ?//可以不看,用不到
?? ??? ??? ?parseQualifierElements(ele, bd);

?? ??? ??? ?bd.setResource(this.readerContext.getResource());
?? ??? ??? ?bd.setSource(extractSource(ele));

?? ??? ??? ?return bd;
?? ??? ?}
?? ??? ??? ?......有興趣自己看

?? ??? ?return null;
?? ?}

打開這個方法parseBeanDefinitionAttributes(),對BeanDefinition屬性進(jìn)行默認(rèn)的封裝,然后返回BeanDefinition對象

public AbstractBeanDefinition parseBeanDefinitionAttributes(Element ele, String beanName,
?? ??? ??? ?@Nullable BeanDefinition containingBean, AbstractBeanDefinition bd) {
?? ??? ?//
?? ??? ?if (ele.hasAttribute(SINGLETON_ATTRIBUTE)) {
?? ??? ??? ?error("Old 1.x 'singleton' attribute in use - upgrade to 'scope' declaration", ele);
?? ??? ?}
?? ??? ?else if (ele.hasAttribute(SCOPE_ATTRIBUTE)) {
?? ??? ??? ?bd.setScope(ele.getAttribute(SCOPE_ATTRIBUTE));
?? ??? ?}
?? ??? ?else if (containingBean != null) {
?? ??? ??? ?// Take default from containing bean in case of an inner bean definition.
?? ??? ??? ?bd.setScope(containingBean.getScope());
?? ??? ?}

?? ??? ?if (ele.hasAttribute(ABSTRACT_ATTRIBUTE)) {
?? ??? ??? ?bd.setAbstract(TRUE_VALUE.equals(ele.getAttribute(ABSTRACT_ATTRIBUTE)));
?? ??? ?}

?? ??? ?String lazyInit = ele.getAttribute(LAZY_INIT_ATTRIBUTE);
?? ??? ?if (isDefaultValue(lazyInit)) {
?? ??? ??? ?lazyInit = this.defaults.getLazyInit();
?? ??? ?}
?? ??? ?bd.setLazyInit(TRUE_VALUE.equals(lazyInit));

?? ??? ?String autowire = ele.getAttribute(AUTOWIRE_ATTRIBUTE);
?? ??? ?bd.setAutowireMode(getAutowireMode(autowire));

?? ??? ?if (ele.hasAttribute(DEPENDS_ON_ATTRIBUTE)) {
?? ??? ??? ?String dependsOn = ele.getAttribute(DEPENDS_ON_ATTRIBUTE);
?? ??? ??? ?bd.setDependsOn(StringUtils.tokenizeToStringArray(dependsOn, MULTI_VALUE_ATTRIBUTE_DELIMITERS));
?? ??? ?}

?? ??? ?String autowireCandidate = ele.getAttribute(AUTOWIRE_CANDIDATE_ATTRIBUTE);
?? ??? ?if (isDefaultValue(autowireCandidate)) {
?? ??? ??? ?String candidatePattern = this.defaults.getAutowireCandidates();
?? ??? ??? ?if (candidatePattern != null) {
?? ??? ??? ??? ?String[] patterns = StringUtils.commaDelimitedListToStringArray(candidatePattern);
?? ??? ??? ??? ?bd.setAutowireCandidate(PatternMatchUtils.simpleMatch(patterns, beanName));
?? ??? ??? ?}
?? ??? ?}
?? ??? ?else {
?? ??? ??? ?bd.setAutowireCandidate(TRUE_VALUE.equals(autowireCandidate));
?? ??? ?}

?? ??? ?if (ele.hasAttribute(PRIMARY_ATTRIBUTE)) {
?? ??? ??? ?bd.setPrimary(TRUE_VALUE.equals(ele.getAttribute(PRIMARY_ATTRIBUTE)));
?? ??? ?}

?? ??? ?if (ele.hasAttribute(INIT_METHOD_ATTRIBUTE)) {
?? ??? ??? ?String initMethodName = ele.getAttribute(INIT_METHOD_ATTRIBUTE);
?? ??? ??? ?bd.setInitMethodName(initMethodName);
?? ??? ?}
?? ??? ?else if (this.defaults.getInitMethod() != null) {
?? ??? ??? ?bd.setInitMethodName(this.defaults.getInitMethod());
?? ??? ??? ?bd.setEnforceInitMethod(false);
?? ??? ?}

?? ??? ?if (ele.hasAttribute(DESTROY_METHOD_ATTRIBUTE)) {
?? ??? ??? ?String destroyMethodName = ele.getAttribute(DESTROY_METHOD_ATTRIBUTE);
?? ??? ??? ?bd.setDestroyMethodName(destroyMethodName);
?? ??? ?}
?? ??? ?else if (this.defaults.getDestroyMethod() != null) {
?? ??? ??? ?bd.setDestroyMethodName(this.defaults.getDestroyMethod());
?? ??? ??? ?bd.setEnforceDestroyMethod(false);
?? ??? ?}

?? ??? ?if (ele.hasAttribute(FACTORY_METHOD_ATTRIBUTE)) {
?? ??? ??? ?bd.setFactoryMethodName(ele.getAttribute(FACTORY_METHOD_ATTRIBUTE));
?? ??? ?}
?? ??? ?if (ele.hasAttribute(FACTORY_BEAN_ATTRIBUTE)) {
?? ??? ??? ?bd.setFactoryBeanName(ele.getAttribute(FACTORY_BEAN_ATTRIBUTE));
?? ??? ?}

?? ??? ?return bd;
?? ?}

然后回到processBeanDefinition方法,將BeanDefinition注冊到緩存中,此時看

protected void processBeanDefinition(Element ele, BeanDefinitionParserDelegate delegate) {
?? ??? ?//重點看這個方法,重要程度 5 ,解析document,封裝成BeanDefinition
?? ??? ?BeanDefinitionHolder bdHolder = delegate.parseBeanDefinitionElement(ele);
?? ??? ?if (bdHolder != null) {
?? ??? ??? ?//該方法功能不重要,設(shè)計模式重點看一下,裝飾者設(shè)計模式,加上SPI設(shè)計思想
?? ??? ??? ?bdHolder = delegate.decorateBeanDefinitionIfRequired(ele, bdHolder);
?? ??? ??? ?try {
?? ??? ??? ??? ?//完成document到BeanDefinition對象轉(zhuǎn)換后,對BeanDefinition對象進(jìn)行緩存注冊
?? ??? ??? ??? ?// Register the final decorated instance.
?? ??? ??? ??? ?BeanDefinitionReaderUtils.registerBeanDefinition(bdHolder, getReaderContext().getRegistry());
?? ??? ??? ?}
?? ??? ??? ?catch (BeanDefinitionStoreException ex) {
?? ??? ??? ??? ?getReaderContext().error("Failed to register bean definition with name '" +
?? ??? ??? ??? ??? ??? ?bdHolder.getBeanName() + "'", ele, ex);
?? ??? ??? ?}
?? ??? ??? ?// Send registration event.
?? ??? ??? ?getReaderContext().fireComponentRegistered(new BeanComponentDefinition(bdHolder));
?? ??? ?}
?? ?}

打開registerBeanDefinition方法

public static void registerBeanDefinition(
?? ??? ??? ?BeanDefinitionHolder definitionHolder, BeanDefinitionRegistry registry)
?? ??? ??? ?throws BeanDefinitionStoreException {

?? ??? ?// Register bean definition under primary name.
?? ??? ?String beanName = definitionHolder.getBeanName();
?? ??? ?//完成BeanDefinition的注冊,重點看
?? ??? ?registry.registerBeanDefinition(beanName, definitionHolder.getBeanDefinition());

?? ??? ?//建立別名和 id的映射,這樣就可以根據(jù)別名獲取到id
?? ??? ?// Register aliases for bean name, if any.
?? ??? ?String[] aliases = definitionHolder.getAliases();
?? ??? ?if (aliases != null) {
?? ??? ??? ?for (String alias : aliases) {
?? ??? ??? ??? ?registry.registerAlias(beanName, alias);
?? ??? ??? ?}
?? ??? ?}
?? ?}

打開registerBeanDefinition方法,將創(chuàng)建好的beanDefinition存入map。默認(rèn)標(biāo)簽解析就此完畢

@Override
?? ?public void registerBeanDefinition(String beanName, BeanDefinition beanDefinition)
?? ??? ??? ?throws BeanDefinitionStoreException {

?? ??? ?Assert.hasText(beanName, "'beanName' must not be empty");
?? ??? ?Assert.notNull(beanDefinition, "BeanDefinition must not be null");
?? ??? ?this.beanDefinitionMap.put(beanName, beanDefinition);
?? ?}

以上就是本文的全部內(nèi)容,希望對大家的學(xué)習(xí)有所幫助,也希望大家多多支持腳本之家。

相關(guān)文章

  • Mybatis-Plus主鍵插入null值報錯問題及解決

    Mybatis-Plus主鍵插入null值報錯問題及解決

    這篇文章主要介紹了Mybatis-Plus主鍵插入null值報錯問題及解決方案,具有很好的參考價值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教
    2023-07-07
  • springboot無法從靜態(tài)上下文中引用非靜態(tài)變量的解決方法

    springboot無法從靜態(tài)上下文中引用非靜態(tài)變量的解決方法

    這篇文章主要介紹了springboot無法從靜態(tài)上下文中引用非靜態(tài)變量的解決方法,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友可以參考下
    2019-06-06
  • springmvc+spring+mybatis實現(xiàn)用戶登錄功能(上)

    springmvc+spring+mybatis實現(xiàn)用戶登錄功能(上)

    這篇文章主要為大家詳細(xì)介紹了springmvc+spring+mybatis實現(xiàn)用戶登錄功能,比較基礎(chǔ)的學(xué)習(xí)教程,具有一定的參考價值,感興趣的小伙伴們可以參考一下
    2017-07-07
  • Java 8中Collectors.toMap空指針異常源碼解析

    Java 8中Collectors.toMap空指針異常源碼解析

    這篇文章主要為大家介紹了Java 8中Collectors.toMap空指針異常源碼解析,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪
    2023-08-08
  • java發(fā)起http請求調(diào)用post與get接口的方法實例

    java發(fā)起http請求調(diào)用post與get接口的方法實例

    在實際開發(fā)過程中,我們經(jīng)常需要調(diào)用對方提供的接口或測試自己寫的接口是否合適,下面這篇文章主要給大家介紹了關(guān)于java發(fā)起http請求調(diào)用post與get接口的相關(guān)資料,需要的朋友可以參考下
    2022-08-08
  • Java邏輯運算符之&&、||?與&、?|的區(qū)別及應(yīng)用

    Java邏輯運算符之&&、||?與&、?|的區(qū)別及應(yīng)用

    這篇文章主要介紹了Java邏輯運算符之&&、||?與&、?|的區(qū)別及應(yīng)用的相關(guān)資料,分別是&&、||?與&、?|,并探討了它們在不同應(yīng)用場景中的表現(xiàn)和優(yōu)化效果,需要的朋友可以參考下
    2025-03-03
  • springboot封裝響應(yīng)實體的實例代碼

    springboot封裝響應(yīng)實體的實例代碼

    這篇文章主要介紹了springboot封裝響應(yīng)實體,本文通過實例代碼給大家介紹的非常詳細(xì),對大家的學(xué)習(xí)或工作具有一定的參考借鑒價值,需要的朋友可以參考下
    2023-07-07
  • Java中的FileWriter用法詳解與實戰(zhàn)記錄

    Java中的FileWriter用法詳解與實戰(zhàn)記錄

    這篇文章主要給大家介紹了關(guān)于Java中FileWriter用法的相關(guān)資料,包括寫入字符數(shù)據(jù)到文件、字符數(shù)組和部分字符寫入、配合BufferedWriter使用等方法,同時也解釋了其與OutputStreamWriter,BufferedWriter的異同特性,適合簡單的文件寫入操作,需要的朋友可以參考下
    2024-10-10
  • Java經(jīng)典面試題匯總:多線程

    Java經(jīng)典面試題匯總:多線程

    本篇總結(jié)的是Java多線程相關(guān)的面試題,后續(xù)會持續(xù)更新,希望我的分享可以幫助到正在備戰(zhàn)面試的實習(xí)生或者已經(jīng)工作的同行,如果發(fā)現(xiàn)錯誤還望大家多多包涵,不吝賜教,謝謝
    2021-07-07
  • 使用Java語言實現(xiàn)一個冒泡排序

    使用Java語言實現(xiàn)一個冒泡排序

    冒泡排序也是一種簡單直觀的排序算法,基本思想是多次遍歷要排序的數(shù)組,每次比較相鄰的元素,如果順序不對就交換它們的位置,本篇文章將通過IDE使用 Java 語言實現(xiàn)一個冒泡排序,需要的朋友可以參考下
    2024-03-03

最新評論

裕民县| 刚察县| 潢川县| 张家港市| 乳源| 武宁县| 泗水县| 抚远县| 深水埗区| 鹿泉市| 丽水市| 扎兰屯市| 迁安市| 仪征市| 彭水| 长垣县| 游戏| 彭州市| 和龙市| 禄劝| 蕲春县| 军事| 呈贡县| 化隆| 咸阳市| 康平县| 白城市| 玛沁县| 沙湾县| 湖口县| 通河县| 界首市| 贞丰县| 牙克石市| 大同县| 温宿县| 鄄城县| 即墨市| 屏东市| 新乡市| 尼勒克县|