《SpringBoot判空處理》揭開@Valid與@Validated的面紗

垚森發表於2020-07-09

一、事有起因

  我們在與前端互動的時候,一般會遇到欄位格式校驗及非空非null的校驗,在沒有SpringBoot註解的時候,

我們可能會在service進行處理:

if(null == name){
      throw new BizException("-1", "使用者名稱不能用空");  
}

  要是有20個欄位需要插入,那我們豈不需要書寫20遍這樣的程式碼,當然這種事最直接的解決方式,但作為程式設計師,我們

首要的任務是要能完成需求到程式碼的轉化,同時還要不斷思考如何更加絲滑的寫程式碼,不要重複造輪子。在進入正題之前我們

先認識以下3位老朋友:

 
entity 用於抽象資料庫中的欄位,不斷任何處理
dto/vo/bean 作為前端資料與資料庫的橋樑,一般我們是一個介面,一個dto,我們的判空也是需要結合dto處理
controller 用於接受前端的請求,我們的判空也是在controller層進行的

 

 

 

 

 

  就此我們正式的開始探索Valid與Validated的旅程

二、判空邏輯的具體實現

2.1、使用的包及註解

 

2.2、註解的含義

@Null                被註釋的元素必須為 null   
@NotNull                被註釋的元素必須不為 null    
@AssertTrue              被註釋的元素必須為 true    
@AssertFalse            被註釋的元素必須為 false    
@Min(value)              被註釋的元素必須是一個數字,其值必須大於等於指定的最小值    
@Max(value)             被註釋的元素必須是一個數字,其值必須小於等於指定的最大值    
@DecimalMin(value)        被註釋的元素必須是一個數字,其值必須大於等於指定的最小值    
@DecimalMax(value)        被註釋的元素必須是一個數字,其值必須小於等於指定的最大值    
@Size(max=, min=)         被註釋的元素的大小必須在指定的範圍內    
@Digits (integer, fraction)   被註釋的元素必須是一個數字,其值必須在可接受的範圍內    
@Past                被註釋的元素必須是一個過去的日期    
@Future                被註釋的元素必須是一個將來的日期    
@Pattern(regex=,flag=)     被註釋的元素必須符合指定的正規表示式    
Hibernate Validator      提供的校驗註解:  
@NotBlank(message =)       驗證字串非null,且長度必須大於0    
@Email               被註釋的元素必須是電子郵箱地址    
@Length(min=,max=)        被註釋的字串的大小必須在指定的範圍內    
@NotEmpty              被註釋的字串的必須非空    
@Range(min=,max=,message=)   被註釋的元素必須在合適的範圍內

 

2.3、dto上使用具體需要判斷的註解

@Data
@EqualsAndHashCode(callSuper = false)
@Accessors(chain = true)
public class SiteProjectCreateReq implements Serializable {

    private static final long serialVersionUID=1L;

    @NotEmpty(message = "專案型別不能為空")   //一旦為空就用丟擲異常,我們統一異常處理就會攔截,然後將message資訊給前端
private String type; }

 

2.4、controller使用@Valid開啟註解

public interface SiteProjectApi {

   //如果是集合或者其他資料結構,則需要在介面或者類上加@Validated
@PostMapping(value = "/createProject") SResponseBean createProject(@RequestBody @Validated SRequestBean<List<SiteProjectCreateReq>> createReqs);

//如果入參是entity,那我們加上@Valid即可,dto中註解就可以生效 @PostMapping(value
= "/createProject") SResponseBean createProject2(@RequestBody @Valid SiteProjectCreateReq createReqs);

}
 
@Data
public class SRequestBean<T> implements Serializable {
@Valid
   CommonHeaderReq header;

   @Valid
T body;
}

/**
 *  Validated  加在類或者介面上
 *  Valid  加在具體的entity或者dto
    @validated和@valid都可以用在controller層的引數前面,但這隻能在controller層生效。
*/

 

2.5、當不滿足條件時,獲取錯誤資訊返回

  注意:不同的註解,丟擲的異常可能不一樣,獲取方式也不一樣,可以除錯加上攔截

@RestControllerAdvice()
public class SiteExceptionHandler {

    @ExceptionHandler(MethodArgumentNotValidException.class)
    public Object handleException(HttpServletRequest request, MethodArgumentNotValidException e){
        LoggerUtil.error("出現異常======> [{}] ",e);
//此處獲取
@NotEmpty(message = "專案型別不能為空"),中的message
     String message = e.getBindingResult().getAllErrors().stream().findFirst().get().getDefaultMessage();
     return SResponseUtil.output("01", message); }
}

 

2.6、再說一句

  一般我們拿到需求,產品經理會根據需求,形成原型。前端設計介面,後臺設計資料庫。

針對於非空欄位,一般需要做以下幾點:

  1、前端在發往後端的時候會進行一次攔截。

  2、後端controller進行攔截一次。

  3、生成的swaager文件,需要標明必輸。

  4、資料庫設計,需要設計成非空。

 三、偷得浮生一刻閒

3.1、新鮮事 

  網傳阿里P9員工出軌P7已婚女下屬?

3.2、歌曲推薦

  童年,這首歌相信大家都很熟悉,小時候那份童真每每想起,嘴角總會上揚,這首粵語版,不失另一種韻味。

 

 

3.3、影視推薦

  2001太空漫遊 2001: A Space Odyssey (1968),我個人始終相信人類是渺小的,宇宙若只有人類,豈不白白浪費。

保持敬畏,保持探索精神。

  推薦理由,標新立異,偉大的科幻片。

 

 3.4、養眼桌布

相關文章