SpringBoot + validation 接口參數(shù)校驗的思路詳解
有參數(shù)傳遞的地方都少不了參數(shù)校驗。在web開發(fā)中,前端的參數(shù)校驗是為了用戶體驗,后端的參數(shù)校驗是為了安全。試想一下,如果在controller層中沒有經(jīng)過任何校驗的參數(shù)通過service層、dao層一路來到了數(shù)據(jù)庫就可能導(dǎo)致嚴重的后果,最好的結(jié)果是查不出數(shù)據(jù),嚴重一點就是報錯,如果這些沒有被校驗的參數(shù)中包含了惡意代碼,那就可能導(dǎo)致更嚴重的后果。
實踐
一、引入依賴
<!--引入spring-boot-starter-validation--> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-validation</artifactId> </dependency>
二、使用校驗
在controller層的參數(shù)校驗可以分為兩種場景:
單個參數(shù)校驗
實體類參數(shù)校驗
2.1 單參數(shù)校驗
/**
* 參數(shù)校驗測試 控制類
* @author oyc
*/
@RestController
@RequestMapping("user")
@Validated
public class RequestParamsValidatedController {
private Logger logger = LoggerFactory.getLogger(this.getClass());
@GetMapping
public User test(@NotNull(message = "姓名不能為空") String name,
@NotNull(message = "年齡不能為空") @Max(value = 99, message = "不能大于200歲") Integer age) {
logger.info("name:" + name + " -age:" + age);
return new User(name, age);
}
}
2.2 實體類參數(shù)校驗
/**
* 參數(shù)校驗測試 控制類
* @author oyc
*/
@RestController
@RequestMapping("user")
@Validated
public class RequestParamsValidatedController {
private Logger logger = LoggerFactory.getLogger(this.getClass());
@PostMapping
public User save(@Validated User user) {
logger.info(user.toString());
return user;
}
}
package com.oycbest.springbootvalidated.vo;
import javax.validation.constraints.*;
import java.io.Serializable;
/**
* 用戶實體類
* @author oyc
*/
public class User implements Serializable {
private String userId;
@NotNull(message = "用戶名不能為空")
private String userName;
@NotNull(message = "年齡不能為空")
@Max(value = 100, message = "年齡不能大于100歲")
private int age;
@NotNull(message = "郵箱不能為空")
@Email(message = "郵箱格式不正確")
private String email;
@NotNull(message = "電話號碼不能為空")
private String phoneNumber;
public User(@NotNull(message = "用戶名不能為空") String userName, int age) {
this.userName = userName;
this.age = age;
}
public User() {
}
public User(String userId, @NotNull(message = "用戶名不能為空") String userName, int age, String email, String phoneNumber) {
this.userId = userId;
this.userName = userName;
this.age = age;
this.email = email;
this.phoneNumber = phoneNumber;
}
public String getUserId() {
return userId;
}
public void setUserId(String userId) {
this.userId = userId;
}
public String getUserName() {
return userName;
}
public void setUserName(String userName) {
this.userName = userName;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
public String getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
public String getPhoneNumber() {
return phoneNumber;
}
public void setPhoneNumber(String phoneNumber) {
this.phoneNumber = phoneNumber;
}
@Override
public String toString() {
return "User{" +
"userId='" + userId + '\'' +
", userName='" + userName + '\'' +
", age=" + age +
", email='" + email + '\'' +
", phoneNumber='" + phoneNumber + '\'' +
'}';
}
}
2.3 定義統(tǒng)一異常處理
package com.oycbest.springbootvalidated.exception;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.context.annotation.Bean;
import org.springframework.http.HttpStatus;
import org.springframework.stereotype.Component;
import org.springframework.validation.BindException;
import org.springframework.validation.FieldError;
import org.springframework.validation.beanvalidation.MethodValidationPostProcessor;
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.bind.annotation.ResponseStatus;
import javax.validation.ConstraintViolation;
import javax.validation.ConstraintViolationException;
import javax.validation.ValidationException;
import java.util.List;
import java.util.Set;
/**
* 全局異常處理
*
* @author oyc
*/
@ControllerAdvice
@Component
public class GlobalExceptionHandler {
private Logger logger = LoggerFactory.getLogger(this.getClass());
@Bean
public MethodValidationPostProcessor methodValidationPostProcessor() {
return new MethodValidationPostProcessor();
}
@ExceptionHandler
@ResponseBody
@ResponseStatus(HttpStatus.BAD_REQUEST)
public String handle(ValidationException exception) {
logger.error("請求異常:" + exception.getMessage());
if (exception instanceof ConstraintViolationException) {
ConstraintViolationException exs = (ConstraintViolationException) exception;
Set<ConstraintViolation<?>> violations = exs.getConstraintViolations();
for (ConstraintViolation<?> item : violations) {
//打印驗證不通過的信息
logger.error("請求異常:" + item.getMessage());
}
}
return "請求異常: " + exception.getMessage();
}
@ResponseBody
@ExceptionHandler(value = BindException.class)
public String bindException(Exception e) {
if (e instanceof BindException) {
BindException exs = (BindException) e;
List<FieldError> fieldErrors = exs.getFieldErrors();
for (FieldError item : fieldErrors) {
logger.error("請求異常:" + item.getDefaultMessage());
}
}
logger.error("數(shù)據(jù)綁定異常:" + e.getMessage());
return "數(shù)據(jù)綁定異常";
}
@ResponseBody
@ExceptionHandler(value = Exception.class)
public String defaultException(Exception e) {
logger.error("請求異常:" + e.getMessage());
return "請求異常 " + e.getMessage();
}
}
三、約束性注解(簡單)說明
|
注解 |
功能 |
|
@AssertFalse |
可以為null,如果不為null的話必須為false |
|
@AssertTrue |
可以為null,如果不為null的話必須為true |
|
@DecimalMax |
設(shè)置不能超過最大值 |
|
@DecimalMin |
設(shè)置不能超過最小值 |
|
@Digits |
設(shè)置必須是數(shù)字且數(shù)字整數(shù)的位數(shù)和小數(shù)的位數(shù)必須在指定范圍內(nèi) |
|
@Future |
日期必須在當(dāng)前日期的未來 |
|
@Past |
日期必須在當(dāng)前日期的過去 |
|
@Max |
最大不得超過此最大值 |
|
@Min |
最大不得小于此最小值 |
|
@NotNull |
不能為null,可以是空 |
|
@Null |
必須為null |
|
@Pattern |
必須滿足指定的正則表達式 |
|
@Size |
集合、數(shù)組、map等的size()值必須在指定范圍內(nèi) |
|
|
必須是email格式 |
|
@Length |
長度必須在指定范圍內(nèi) |
|
@NotBlank |
字符串不能為null,字符串trim()后也不能等于“” |
|
@NotEmpty |
不能為null,集合、數(shù)組、map等size()不能為0;字符串trim()后可以等于“” |
|
@Range |
值必須在指定范圍內(nèi) |
|
@URL |
必須是一個URL |
到此這篇關(guān)于SpringBoot + validation 接口參數(shù)校驗的文章就介紹到這了,更多相關(guān)SpringBoot + validation 接口參數(shù)校驗內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
- Spring?Boot集成validation實現(xiàn)參數(shù)校驗功能
- SpringBoot使用Validation包進行輸入?yún)?shù)校驗
- spring?boot?validation參數(shù)校驗與分組嵌套各種類型及使用小結(jié)
- springboot中使用Hibernate-Validation校驗參數(shù)詳解
- SpringBoot使用Validation進行參數(shù)校驗的示例詳解
- spring-boot-starter-validation?校驗參數(shù)的實現(xiàn)
- spring boot輸入數(shù)據(jù)校驗(validation)的實現(xiàn)過程
- 從零到掌握Spring Boot Validation 接口校驗的詳細過程
相關(guān)文章
基于Springboot+Junit+Mockito做單元測試的示例
本篇文章主要介紹了基于Springboot+Junit+Mockito做單元測試的示例,小編覺得挺不錯的,現(xiàn)在分享給大家,也給大家做個參考。一起跟隨小編過來看看吧2018-02-02
Java編程發(fā)展歷史(動力節(jié)點Java學(xué)院整理)
Java的歷史可以追溯到1991年4月,Sun公司的James Gosling領(lǐng)導(dǎo)的綠色計劃(Green Project)開始著力發(fā)展一種分布式系統(tǒng)結(jié)構(gòu),使其能夠在各種消費性電子產(chǎn)品上運行,他們使用了C/C++/Oak語言。由于多種原因,綠色計劃逐漸陷于停滯狀態(tài)2017-03-03
Spring使用@Filter注解創(chuàng)建自定義過濾器
Spring 中鮮為人知但非常有用的注解之一是 @Filter,它支持自定義過濾器,下面我們就來深入研究一下如何使用 Spring 的 @Filter 注解來創(chuàng)建自定義過濾器吧2023-11-11

