久久福利_99r_国产日韩在线视频_直接看av的网站_中文欧美日韩_久久一

您的位置:首頁技術文章
文章詳情頁

Java Validation Api實現原理解析

瀏覽:14日期:2022-08-25 13:32:18

前言:

涉及知識點:AOP、攔截器相關

功能主要實現類:因為bean validation只提供了接口并未實現,使用時需要加上一個provider的包,例如hibernate-validator

范圍: 注解:@Valid @RequestBudy

主要實現類:RequestResponseBodyMethodProcessor

處理器:HandlerMethodArgumentResolver

注解說明:

@Valid:標準JSR-303規范的標記型注解,用來標記驗證屬性和方法返回值,進行級聯和遞歸校驗,@Valid可用于方法、字段、構造器和參數上 @RequestBudy 請求的Body體,只能被讀取一次

RequestResponseBodyMethodProcessor 類說明:

// @since 3.1public class RequestResponseBodyMethodProcessor extends AbstractMessageConverterMethodProcessor { @Override public boolean supportsParameter(MethodParameter parameter) { return parameter.hasParameterAnnotation(RequestBody.class); } // 類上或者方法上標注了@ResponseBody注解都行 @Override public boolean supportsReturnType(MethodParameter returnType) { return (AnnotatedElementUtils.hasAnnotation(returnType.getContainingClass(), ResponseBody.class) || returnType.hasMethodAnnotation(ResponseBody.class)); } // 這是處理入參封裝校驗的入口,也是本文關注的焦點 @Override public Object resolveArgument(MethodParameter parameter, @Nullable ModelAndViewContainer mavContainer, NativeWebRequest webRequest, @Nullable WebDataBinderFactory binderFactory) throws Exception { // 它是支持`Optional`容器的 parameter = parameter.nestedIfOptional(); // 使用消息轉換器HttpInputMessage把request請求轉換出來,拿到值~~~ // 此處注意:比如本例入參是Person類,所以經過這里處理會生成一個空的Person對象出來(反射) Object arg = readWithMessageConverters(webRequest, parameter, parameter.getNestedGenericParameterType()); // 獲取到入參的名稱,其實不叫形參名字,應該叫objectName給校驗時用的 // 請注意:這里的名稱是類名首字母小寫,并不是你方法里寫的名字。比如本利若形參名寫為personAAA,但是name的值還是person // 但是注意:`parameter.getParameterName()`的值可是personAAA String name = Conventions.getVariableNameForParameter(parameter); // 只有存在binderFactory才會去完成自動的綁定、校驗~ // 此處web環境為:ServletRequestDataBinderFactory if (binderFactory != null) { WebDataBinder binder = binderFactory.createBinder(webRequest, arg, name); // 顯然傳了參數才需要去綁定校驗嘛 if (arg != null) {// 這里完成數據綁定+數據校驗~~~~~(綁定的錯誤和校驗的錯誤都會放進Errors里)// Applicable:適合validateIfApplicable(binder, parameter);// 若有錯誤消息hasErrors(),并且僅跟著的一個參數不是Errors類型,Spring MVC會主動給你拋出MethodArgumentNotValidException異常// 否則,調用者自行處理if (binder.getBindingResult().hasErrors() && isBindExceptionRequired(binder, parameter)) { throw new MethodArgumentNotValidException(parameter, binder.getBindingResult());} } // 把錯誤消息放進去 證明已經校驗出錯誤了~~~ // 后續邏輯會判斷MODEL_KEY_PREFIX這個key的~~~~ if (mavContainer != null) {mavContainer.addAttribute(BindingResult.MODEL_KEY_PREFIX + name, binder.getBindingResult()); } } return adaptArgumentIfNecessary(arg, parameter); } // 校驗,如果合適的話。使用WebDataBinder,失敗信息最終也都是放在它身上~ 本方法是本文關注的焦點 // 入參:MethodParameter parameter protected void validateIfApplicable(WebDataBinder binder, MethodParameter parameter) { // 拿到標注在此參數上的所有注解們(比如此處有@Valid和@RequestBody兩個注解) Annotation[] annotations = parameter.getParameterAnnotations(); for (Annotation ann : annotations) { // 先看看有木有@Validated Validated validatedAnn = AnnotationUtils.getAnnotation(ann, Validated.class); // 這個里的判斷是關鍵:可以看到標注了@Validated注解 或者注解名是以Valid打頭的 都會有效哦 //注意:這里可沒說必須是@Valid注解。實際上你自定義注解,名稱只要一Valid開頭都成~~~~~ if (validatedAnn != null || ann.annotationType().getSimpleName().startsWith('Valid')) {// 拿到分組group后,調用binder的validate()進行校驗~~~~// 可以看到:拿到一個合適的注解后,立馬就break了~~~// 所以若你兩個主機都標注@Validated和@Valid,效果是一樣滴~Object hints = (validatedAnn != null ? validatedAnn.value() : AnnotationUtils.getValue(ann));Object[] validationHints = (hints instanceof Object[] ? (Object[]) hints : new Object[] {hints});binder.validate(validationHints);break; } } } ...}

可以看得,這個類應該是陌生的,它能夠處理@ResponseBody注解返回值;它還有另一個能力是:它能夠處理請求參數(當然也是標注了@RequestBody的JavaBean)所以它既是個處理返回值的HandlerMethodReturnValueHandler,又是一個處理入參的HandlerMethodArgumentResolver。所以它命名為Processor而不是Resolver/Handler。

這是使用@RequestBody結合@Valid完成數據校驗的基本原理。其實當Spring MVC在處理@RequestPart注解入參數據時,也會執行綁定、校驗的相關邏輯。對應處理器是RequestPartMethodArgumentResolver,原理大體上和這相似,它主要處理Multipart相關,本文忽略~

以上就是dui’y對于@Valid標注的@RequestBody的JavaBean的原理說明,敬請指點。

以上就是本文的全部內容,希望對大家的學習有所幫助,也希望大家多多支持好吧啦網。

標簽: Java
相關文章:
主站蜘蛛池模板: 国产欧美日韩 | 免费大片黄在线观看 | 亚洲日本精品视频 | 久久久精品一区二区 | 国产精品久久久久久久久大全 | 精品视频久久久 | 一区久久 | 精品久久久久久久 | 天天拍天天操 | 亚洲一区在线观看视频 | 精品成人av | 欧洲亚洲精品久久久久 | 高清成人 | 日韩高清黄色 | 亚洲一区二区视频在线播放 | 久久国产高清 | 欧美aaa视频 | 国产精品久久久久久婷婷天堂 | 精品国产欧美一区二区 | 久草热视频| 国产精品国产三级国产aⅴ9色 | 精品国产影院 | 一区二区中文字幕 | 精品视频久久 | 男女视频在线观看 | 久久久久综合 | 中文字幕一区二区三 | 欧美精品一区二区久久 | 污视频在线观看免费 | 天堂在线中文 | 久久aⅴ乱码一区二区三区 91综合网 | 久久久精品高清 | 久久久久一区二区 | 综合精品| 黄篇网址 | 免费观看一级特黄欧美大片 | 国产高清一区 | 亚洲午夜性视频 | 99在线视频精品 | 国产成人精品一区二区三区视频 | 国产精品视频一区二区三区四蜜臂 |