日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程语言 > c/c++ >内容正文

c/c++

mvc:annotation-driven/

發布時間:2024/6/21 c/c++ 37 豆豆
生活随笔 收集整理的這篇文章主要介紹了 mvc:annotation-driven/ 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

轉自:?Spring MVC 解讀——<mvc:annotation-driven/>

摘自:使用@Controller注解為什么要配置<mvc:annotation-driven />

?

?

摘要: <mvc:annotation-driven/>是做什么的?它做了什么?它與<context:component-scan/>有什么區別?

Spring MVC 解讀——<mvc:annotation-driven/>

一、AnnotationDrivenBeanDefinitionParser

????通常如果我們希望通過注解的方式來進行Spring MVC開發,我們都會在***-servlet.xml中加入<mvc:annotation-driven/>標簽來告訴Spring我們的目的。但是我們為什么這么做呢?這個標簽是什么意思呢?它做了什么呢?

????同樣為了弄清楚這些問題, 像<context:component-scan/>標簽一樣,我們先找到它的解析類。第一篇文章中說過了,所有的自定義命名空間(像mvc,context等)下的標簽解析都是由BeanDefinitionParser接口的子類來完成的。參看第一篇文章中的圖片

?

我們看到有多個AnnotationDrivenBeanDefinitionParser,他們是用來處理不同命名空間下的<annotation-driven/>標簽的,我們今天研究的是<mvc:annotation-driven/>標簽,所以我們找到對應的實現類是org.springframework.web.servlet.config.AnnotationDrivenBeanDefinitionParser。
????通過閱讀類注釋文檔,我們發現這個類主要是用來向工廠中注冊了

  • RequestMappingHandlerMapping?

  • BeanNameUrlHandlerMapping

  • RequestMappingHandlerAdapter

  • HttpRequestHandlerAdapter

  • SimpleControllerHandlerAdapter

  • ExceptionHandlerExceptionResolver?

  • ResponseStatusExceptionResolver?

  • DefaultHandlerExceptionResolver?

上面幾個Bean實例。這幾個類都是用來做什么的呢?

????前兩個是HandlerMapping接口的實現類,用來處理請求映射的。其中第一個是處理@RequestMapping注解的。第二個會將controller類的名字映射為請求url。

????中間三個是用來處理請求的。具體點說就是確定調用哪個controller的哪個方法來處理當前請求。第一個處理@Controller注解的處理器,支持自定義方法參數和返回值(很酷)。第二個是處理繼承HttpRequestHandler的處理器。第三個處理繼承自Controller接口的處理器。

????后面三個是用來處理異常的解析器。

二、實現

????光說無憑據,我們直接看代碼:

public BeanDefinition parse(Element element, ParserContext parserContext) {Object source = parserContext.extractSource(element);CompositeComponentDefinition compDefinition = new CompositeComponentDefinition(element.getTagName(), source);parserContext.pushContainingComponent(compDefinition);RuntimeBeanReference contentNegotiationManager = getContentNegotiationManager(element, source, parserContext);//第一個在這 RequestMappingHandlerMappingRootBeanDefinition handlerMappingDef = new RootBeanDefinition(RequestMappingHandlerMapping.class);handlerMappingDef.setSource(source);handlerMappingDef.setRole(BeanDefinition.ROLE_INFRASTRUCTURE);handlerMappingDef.getPropertyValues().add("order", 0);handlerMappingDef.getPropertyValues().add("removeSemicolonContent", false);handlerMappingDef.getPropertyValues().add("contentNegotiationManager", contentNegotiationManager);String methodMappingName = parserContext.getReaderContext().registerWithGeneratedName(handlerMappingDef);//第二個在這 RequestMappingHandlerAdapterRootBeanDefinition handlerAdapterDef = new RootBeanDefinition(RequestMappingHandlerAdapter.class);handlerAdapterDef.setSource(source);handlerAdapterDef.setRole(BeanDefinition.ROLE_INFRASTRUCTURE);handlerAdapterDef.getPropertyValues().add("contentNegotiationManager", contentNegotiationManager);handlerAdapterDef.getPropertyValues().add("webBindingInitializer", bindingDef);handlerAdapterDef.getPropertyValues().add("messageConverters", messageConverters);if (element.hasAttribute("ignoreDefaultModelOnRedirect")) {Boolean ignoreDefaultModel = Boolean.valueOf(element.getAttribute("ignoreDefaultModelOnRedirect"));handlerAdapterDef.getPropertyValues().add("ignoreDefaultModelOnRedirect", ignoreDefaultModel);}if (argumentResolvers != null) {handlerAdapterDef.getPropertyValues().add("customArgumentResolvers", argumentResolvers);}if (returnValueHandlers != null) {handlerAdapterDef.getPropertyValues().add("customReturnValueHandlers", returnValueHandlers);}if (asyncTimeout != null) {handlerAdapterDef.getPropertyValues().add("asyncRequestTimeout", asyncTimeout);}if (asyncExecutor != null) {handlerAdapterDef.getPropertyValues().add("taskExecutor", asyncExecutor);}handlerAdapterDef.getPropertyValues().add("callableInterceptors", callableInterceptors);handlerAdapterDef.getPropertyValues().add("deferredResultInterceptors", deferredResultInterceptors);String handlerAdapterName = parserContext.getReaderContext().registerWithGeneratedName(handlerAdapterDef);//異常處理解析器RootBeanDefinition exceptionHandlerExceptionResolver = new RootBeanDefinition(ExceptionHandlerExceptionResolver.class);exceptionHandlerExceptionResolver.setSource(source);exceptionHandlerExceptionResolver.setRole(BeanDefinition.ROLE_INFRASTRUCTURE);exceptionHandlerExceptionResolver.getPropertyValues().add("contentNegotiationManager", contentNegotiationManager);exceptionHandlerExceptionResolver.getPropertyValues().add("messageConverters", messageConverters);exceptionHandlerExceptionResolver.getPropertyValues().add("order", 0);String methodExceptionResolverName =parserContext.getReaderContext().registerWithGeneratedName(exceptionHandlerExceptionResolver);//異常處理解析器RootBeanDefinition responseStatusExceptionResolver = new RootBeanDefinition(ResponseStatusExceptionResolver.class);responseStatusExceptionResolver.setSource(source);responseStatusExceptionResolver.setRole(BeanDefinition.ROLE_INFRASTRUCTURE);responseStatusExceptionResolver.getPropertyValues().add("order", 1);String responseStatusExceptionResolverName =parserContext.getReaderContext().registerWithGeneratedName(responseStatusExceptionResolver);//異常處理解析器RootBeanDefinition defaultExceptionResolver = new RootBeanDefinition(DefaultHandlerExceptionResolver.class);defaultExceptionResolver.setSource(source);defaultExceptionResolver.setRole(BeanDefinition.ROLE_INFRASTRUCTURE);defaultExceptionResolver.getPropertyValues().add("order", 2);String defaultExceptionResolverName =parserContext.getReaderContext().registerWithGeneratedName(defaultExceptionResolver);parserContext.registerComponent(new BeanComponentDefinition(handlerMappingDef, methodMappingName));parserContext.registerComponent(new BeanComponentDefinition(handlerAdapterDef, handlerAdapterName));parserContext.registerComponent(new BeanComponentDefinition(exceptionHandlerExceptionResolver, methodExceptionResolverName));parserContext.registerComponent(new BeanComponentDefinition(responseStatusExceptionResolver, responseStatusExceptionResolverName));parserContext.registerComponent(new BeanComponentDefinition(defaultExceptionResolver, defaultExceptionResolverName));parserContext.registerComponent(new BeanComponentDefinition(mappedCsInterceptorDef, mappedInterceptorName));//這里注冊了BeanNameUrlHandlerMapping,SimpleControllerHandlerAdapter等// Ensure BeanNameUrlHandlerMapping (SPR-8289) and default HandlerAdapters are not "turned off" MvcNamespaceUtils.registerDefaultComponents(parserContext, source);parserContext.popAndRegisterContainingComponent();return null;} //在這啊。 public static void registerDefaultComponents(ParserContext parserContext, Object source) {registerBeanNameUrlHandlerMapping(parserContext, source);registerHttpRequestHandlerAdapter(parserContext, source);registerSimpleControllerHandlerAdapter(parserContext, source);}

略長,但很容易看明白的代碼。看注釋我們發現,它的確注冊了上面說的那幾個類。

三、總結

????我們知道了它們自動為我們注冊了這么多的Bean,那這些Bean是做什么的呢?

????我們主要說明里面的兩個,RequestMappingHandlerMapping和RequestMappingHandlerAdapter。

????第一個是HandlerMapping的實現類,它會處理@RequestMapping 注解,并將其注冊到請求映射表中。(下片文章我們會詳細介紹的)

????第二個是HandlerAdapter的實現類,它是處理請求的適配器,說白了,就是確定調用哪個類的哪個方法,并且構造方法參數,返回值。(后面文章也會陸續詳細介紹的)

????那么它跟<context:component-scan/>有什么區別呢?其實想上篇文章中介紹的,<context:component-scan/>標簽是告訴Spring 來掃描指定包下的類,并注冊被@Component,@Controller,@Service,@Repository等注解標記的組件。

????而<mvc:annotation-scan/>是告知Spring,我們啟用注解驅動。然后Spring會自動為我們注冊上面說到的幾個Bean到工廠中,來處理我們的請求。

?

?

------------------------------------------------


?

This tag registers the DefaultAnnotationHandlerMapping and AnnotationMethodHandlerAdapter beans that are required for spring MVC to dispatch requests to Controllers.?
這個標簽注冊了Spring MVC分發請求到控制器所必須的DefaultAnnotationHandlerMapping和AnnotationMethodHandlerAdapter實例

The tag configures those two beans with sensible defaults based on what is present in your classpath.?
標簽配置的這2個實例可以根據classpath中的內容默認提供以下功能:

The defaults are:
1. Support for Spring 3's Type ConversionService in addition to JavaBeans PropertyEditors during Data Binding.?
A ConversionService instance produced by the org.springframework.format.support.FormattingConversionServiceFactoryBean is used by default.?
This can be overriden by setting the conversion-service attribute.
支持spring3的javaBeans屬性編輯器數據綁定時的類型轉換服務。
類型轉換服務實例默認為org.springframework.format.support.FormattingConversionServiceFactoryBean。
可以覆蓋conversion-service屬性來指定類型轉換服務實例類。

2. Support for formatting Number fields using the @NumberFormat annotation
支持@NumberFormat 注解格式化數字類型字段。

3. Support for formatting Date, Calendar, Long, and Joda Time fields using the @DateTimeFormat annotation, if Joda Time 1.3 or higher is present on the classpath.
@DateTimeFormat注解格式化 Date, Calendar, Long和 Joda Time(如classpath下存在Joda Time 1.3或更高版本)字段

4. Support for validating @Controller inputs with @Valid, if a JSR-303 Provider is present on the classpath.?
The validation system can be explicitly configured by setting the validator attribute.
支持@Valid注解驗證控制器數據,classpath中需JSR-303的**。
可以使用setting明確的配置

5. Support for reading and writing XML, if JAXB is present on the classpath.
支持讀寫xml,classpath中需JAXB 。

6. Support for reading and writing JSON, if Jackson is present on the classpath.
支持讀寫json,classpath中需Jackson 。

A typical usage is shown below:
下邊是用法:

<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:mvc="http://www.springframework.org/schema/mvc" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation=" http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.0.xsd http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc-3.0.xsd"> <!-- JSR-303 support will be detected on classpath and enabled automatically --> <mvc:annotation-driven/> </beans>

?

?

轉載于:https://www.cnblogs.com/drizzlewithwind/p/6064021.html

總結

以上是生活随笔為你收集整理的mvc:annotation-driven/的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。

主站蜘蛛池模板: 精精国产xxxx视频在线播放 | 宅男av | 在线观看成人av | 日韩在线www | 日本老师巨大bbw丰满 | 自拍视频在线播放 | 乱一色一乱一性一视频 | 三女同志亚洲人狂欢 | wwwjizzzcom| 岛国av一区二区 | xxxxx在线视频| 伊人狠狠操 | 色婷婷综合久久久中文字幕 | 羞羞答答一区 | 免费在线性爱视频 | 久久综合久久综合久久 | 宅男在线视频 | 亚洲4p| 伊人免费在线 | 日本a级c片免费看三区 | 名人明星三级videos | 国产精品2019 | 尤物一区二区 | av性天堂网 | 亚洲国产精品av | 亚洲欧美在线观看视频 | 精品久久综合 | 国产91绿帽单男绿奴 | 日本打白嫩屁股视频 | 黑人玩弄人妻一区二区绿帽子 | 无码人妻丰满熟妇区五十路百度 | 99热99精品 | 无码视频一区二区三区 | 成人拍拍视频 | 日本不卡一区二区在线观看 | 欧美丰满美乳xxⅹ高潮www | 久久久久久久9 | 午夜精品视频 | 大乳村妇的性需求 | 日日操狠狠操 | 成人在线免费 | 色啪综合 | 天天干狠狠插 | 99国产精品白浆在线观看免费 | 国产女主播在线 | 动漫毛片 | 日本一区二区免费视频 | 免费在线成人网 | 亚洲av无码专区在线 | 少妇免费看| 欧美日韩在线中文字幕 | 亚洲欧洲天堂 | 91chinese在线| 欧美老肥妇做.爰bbww视频 | 美女100%露胸无遮挡 | 亚洲欧美综合在线观看 | 欧美亚洲另类图片 | 亚洲天堂资源 | 人妻射精一区二区 | 色就是色亚洲色图 | 99久久婷婷 | 精品日韩制服无码久久久久久 | 国产精品无码一区二区三区在线看 | www.久草.com| 日本精品人妻无码免费大全 | 秋霞国产一区 | 日日夜夜骑 | 亚洲欧美自拍另类 | 影音先锋成人在线 | 国产在线黄色 | 侵犯亲女在线播放视频 | 国产精品国产三级国产aⅴ无密码 | 国产精品--色哟哟 | 精品欧美激情精品一区 | av有声小说一区二区三区 | 在线观看福利电影 | 那里可以看毛片 | 日本一二三视频 | 老女人性视频 | 中文字幕人妻互换av久久 | 亚洲自拍中文字幕 | 国产又黄又爽视频 | 九九热超碰 | 久久精品一区二区在线观看 | 亚洲第8页| 黄色网络在线观看 | 日本久久久久久久久久久 | 九九爱精品视频 | 国产亚洲精品久久久久丝瓜 | 亚洲尤物视频 | 免费欧美一级 | 欧美一区二区在线看 | 少妇一晚三次一区二区三区 | 亚洲无人禁区 | 中文字幕一区二区三区在线观看 | 91激情在线观看 | 一区二区不卡在线观看 | 国产精品国产三级国产三级人妇 | 麻豆亚洲av成人无码久久精品 |