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

Spring?Validation接口入?yún)⑿r?yàn)示例代碼

 更新時(shí)間:2023年06月19日 16:26:08   作者:programmer_山風(fēng)  
Spring?Validation是一種用于實(shí)現(xiàn)數(shù)據(jù)校驗(yàn)的框架,它提供了一系列的校驗(yàn)器,針對不同的數(shù)據(jù)類型可以使用不同的校驗(yàn)器進(jìn)行校驗(yàn),下面這篇文章主要給大家介紹了關(guān)于Spring?Validation接口入?yún)⑿r?yàn)的相關(guān)資料,需要的朋友可以參考下

一、前言

JSR 是 Java Specification Requests 的縮寫,含義為 JAVA 規(guī)范提案。

JSR 303 - Bean Validation 規(guī)范, 正是一套基于 JavaBean 參數(shù)校驗(yàn)的標(biāo)準(zhǔn)。

Hibernate Validator 是 JSR 303 的實(shí)現(xiàn),它提供了 JSR 303 規(guī)范中所有約束(constraint)的實(shí)現(xiàn),同時(shí)也對其作出一些拓展。

Spring Validation 是對 Hibernate validation 的二次封裝,用于支持 Spring MVC 參數(shù)校驗(yàn)。

?? JSR 303 包含的注解:

驗(yàn)證注解

驗(yàn)證數(shù)據(jù)類型

說明

@Null

任意類型

元素值為 Null

@NotNull

任意類型

元素值不為 Null

@AssertTrue

Bool

元素為 true

@AssertFalse

Bool

元素為 false

@Min(value = 最小值)

BigDecimal、BigInteger、byte、short、int、long 等 Number 或 CharSequence (數(shù)字)子類型

元素值需大于等于指定值

@Max(value = 最大值)

BigDecimal、BigInteger、byte、short、int、long 等 Number 或 CharSequence (數(shù)字)子類型

元素值需小于等于指定值

@DecimalMin(value = 最小值)

BigDecimal、BigInteger、byte、short、int、long 等 Number 或 CharSequence (數(shù)字)子類型

元素值需大于等于指定值

@DecimalMax(value = 最大值)

BigDecimal、BigInteger、byte、short、int、long 等 Number 或 CharSequence (數(shù)字)子類型

元素值需小于等于指定值

@Size(min = 最小值, max = 最大值)

String、Collection、Array 等

元素值的字符長度/集合大小需在指定的區(qū)間范圍內(nèi)

@Digits(integer = 整數(shù)位數(shù), fraction = 小數(shù)位數(shù))

BigDecimal、BigInteger、byte、short、int、long 等 Number 或 CharSequence (數(shù)字)子類型

元素值整數(shù)位、小數(shù)位需小于對應(yīng)指定值

@Past

DATE、Calendar、Time 等日期

元素值需在指定時(shí)間之前

@Future

DATE、Calendar、Time 等日期

元素值需在指定時(shí)間之后

@Pattern(regexp = 正則式, flag = 標(biāo)志的模式)

String 等

元素值與指定的正則式匹配

??hibernate.validator 擴(kuò)展的注解:

驗(yàn)證注解

驗(yàn)證數(shù)據(jù)類型

說明

@NotBlank

String 等 CharSequence 子類型

元素值不為空串(字符串不為 Null 且去除首尾空格后長度不為 0)

@Email(regexp = 正則式, flag = 標(biāo)志的模式)

String 等

元素值為電子郵箱格式,可通過 regexp、flag 屬性指定格式

@Length(min = 最小值, max = 最大值)

String 等

元素值長度在指定區(qū)間范圍內(nèi)

@NotEmpty

String、Collection、Array 等

元素值不為 Null 且長度不為 0

@Range(min = 最小值, max = 最大值)

BigDecimal、BigInteger、byte、short、int、long 等 Number 或 CharSequence (數(shù)字)子類型

元素值在指定區(qū)間范圍內(nèi)

@URL

String 等

元素值必須時(shí)合法的URL

二、Spring Validation的使用

1、在項(xiàng)目pom.xml中引入依賴

<!-- JSR 303 -->
<dependency>
    <groupId>javax.validation</groupId>
    <artifactId>validation-api</artifactId>
</dependency>
<!-- 在 SpringBoot 項(xiàng)目中,若 SpringBoot 版本小于 2.3.x ,則此依賴已包含在 spring-boot-starter-web 中,無需添加額外依賴;
若 SpringBoot 版本大于 2.3.x ,則需手動(dòng)引入依賴。-->
<!-- Hibernate Validator -->
<dependency>
    <groupId>org.hibernate.validator</groupId>
    <artifactId>hibernate-validator</artifactId>
</dependency>

2、 參數(shù)注解校驗(yàn)的使用場景

場景一:直接入?yún)⒌男r?yàn)

①在類上添加 @Validated 注解,否則參數(shù)校驗(yàn)無法生效;

②入?yún)⒅惺褂米⒔?@NotEmpty 等;

@Validated
@RestController
@RequestMapping("/user")
public class UserController {
    @GetMapping("/saveUserName")
    public String saveUserInfo(@NotEmpty String userName) {
        System.out.println("userName:"+ userName +",保存成功");
        return "success";
    }
}

測試:

【請求URL】:
http://192.168.1.7:27100/user/saveUserName?userName=
 
【執(zhí)行結(jié)果】:
嚴(yán)重: Servlet.service() for servlet [dispatcherServlet] in context with path [] threw exception [Request processing failed; nested exception is javax.validation.ConstraintViolationException: saveUserInfo.userName: 不能為空] with root cause
javax.validation.ConstraintViolationException: saveUserInfo.userName: 不能為空
    at org.springframework.validation.beanvalidation.MethodValidationInterceptor.invoke(MethodValidationInterceptor.java:116)
    at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:186)
    at org.springframework.aop.framework.CglibAopProxy$DynamicAdvisedInterceptor.intercept(CglibAopProxy.java:688)
……

場景二:對象模型屬性的校驗(yàn)

1、創(chuàng)建 User對象

@Data
public class User {
    private Integer id;
    @NotEmpty(message = "用戶名不能為空")
    private String userName;
    private Integer age;
    @NotNull(message = "用戶密碼不能為空")
    @Size(min = 5, max = 10,message = "密碼長度必須是5-10個(gè)字符")
    private String password;
}

2、全局異常捕獲

@RestControllerAdvice
public class GlobalExceptionHandler {
    /**
     * 方法直接入?yún)⑿r?yàn)
     *
     * @param ex
     * @return
     */
    @ExceptionHandler(ConstraintViolationException.class)
    public BaseResult resolveConstraintViolationException(ConstraintViolationException ex) {
        Set<ConstraintViolation<?>> constraintViolations = ex.getConstraintViolations();
        if (!CollectionUtils.isEmpty(constraintViolations)) {
            String errorMessage = constraintViolations.stream().map(ConstraintViolation::getMessage).collect(Collectors.joining(", "));
            return BaseResult.fail(ResultEnum.ILLEGAL_PARAMETER, errorMessage);
        }
        return BaseResult.fail(ResultEnum.ILLEGAL_PARAMETER, ex.getMessage());
    }
    /**
     * 對象模型屬性校驗(yàn)
     *
     * @param ex
     * @return
     */
    @ExceptionHandler(MethodArgumentNotValidException.class)
    public BaseResult resolveMethodArgumentNotValidException(MethodArgumentNotValidException ex) {
        List<ObjectError> allErrors = ex.getBindingResult().getAllErrors();
        if (!CollectionUtils.isEmpty(allErrors)) {
            String errorMessage = allErrors.stream().map(ObjectError::getDefaultMessage).collect(Collectors.joining(", "));
            return BaseResult.fail(ResultEnum.ILLEGAL_PARAMETER, errorMessage);
        }
        return BaseResult.fail(ResultEnum.ILLEGAL_PARAMETER, ex.getMessage());
    }
}

3、通用返回結(jié)構(gòu)體

@Data
@AllArgsConstructor
@NoArgsConstructor
@Accessors(chain = true)
public class BaseResult<T> {
    private Integer code;
    private String message;
    private T data;
    public static <T> BaseResult<T> success() {
        return new BaseResult(ResultEnum.SUCCESS.getCode(), ResultEnum.SUCCESS.getMsg(), new JSONObject());
    }
    public static <T> BaseResult<T> fail(ResultEnum resultEnum, T data) {
        return fail(resultEnum.getCode(), resultEnum.getMsg(), data);
    }
    @Override
    public String toString() {
        return "BaseResult{" +
                "code=" + code +
                ", message='" + message + '\'' +
                ", data=" + data +
                '}';
    }
}

4、錯(cuò)誤提示碼枚舉類

/**
 * 錯(cuò)誤提示碼
 */
public enum ResultEnum {
    /** 狀態(tài)碼:未知錯(cuò)誤 **/
    UNKNOWN_ERROR(-1, "未知錯(cuò)誤"),
    /** 狀態(tài)碼:成功 **/
    SUCCESS(0, "成功"),
    /** 狀態(tài)碼:失敗 **/
    FAIL(1,"失敗"),
    /** 狀態(tài)碼:非法參數(shù) **/
    ILLEGAL_PARAMETER(2,"非法參數(shù)");
    private Integer code;
    private String msg;
    ResultEnum(Integer code, String msg) {
        this.code = code;
        this.msg = msg;
    }
    public Integer getCode() {
        return code;
    }
    public String getMsg() {
        return msg;
    }
}

5、暴露的接口

① 在類上添加 @Validated 注解,否則參數(shù)校驗(yàn)無法生效;

② 在入?yún)?shí)體前添加 @Validated 注解;

@Validated
@RestController
@RequestMapping("/user")
public class UserController {
    @PostMapping("/saveUserInfo")
    public String saveUserInfo(@RequestBody @Validated User user) {
        System.out.println("userName:"+ user.getUserName() +",保存成功");
        return "success";
    }
}

6、測試:

【請求URL】:http://192.168.1.7:27100/user/saveUserInfo
【請求方式】:POST
【請求參數(shù)】:
{
   "userName":"張三"
}
 
【執(zhí)行結(jié)果】:
{
     "code": 2,
     "message": "非法參數(shù)",
     "data": "用戶密碼不能為空"
}

場景三:參數(shù)注解校驗(yàn)的分組驗(yàn)證

1、新建分組接口

/**
 * 分組接口:新增
 */
public interface Add {
}
/**
 * 分組接口:更新
 */
public interface Update {
}

2、在校驗(yàn)注解中使用 groups 屬性標(biāo)明分組

@Data
public class User {
 
    @NotNull(message = "更新數(shù)據(jù)時(shí),主鍵id不能為空", groups = Update.class)
    private Integer id;
 
    @NotEmpty(message = "用戶名不能為空")
    private String userName;
    
    private Integer age;
 
    @NotNull(message = "用戶密碼不能為空")
    @Size(min = 5, max = 10,message = "密碼長度必須是5-10個(gè)字符")
    private String password;
}

【注】需要注意的是實(shí)體類中所有字段注解校驗(yàn)規(guī)則默認(rèn)屬于 Default 分組,接口入?yún)?@Validated 注解默認(rèn)檢驗(yàn) Default 分組的校驗(yàn)規(guī)則。當(dāng)接口入?yún)⑹褂?@Validated 顯式聲明非默認(rèn)分組時(shí),實(shí)體類中所有未顯式聲明分組的注解校驗(yàn)將不會生效。

3、處理器方法

@Validated
@RestController
@RequestMapping("/user")
public class UserController {
    @PostMapping("/updateUserInfo")
    public String updateUserInfo(@RequestBody @Validated({Update.class}) User user) {
        System.out.println("id:" + user.getId() + ",userName:"+ user.getUserName() +",更新成功");
        return "success";
    }
}

4、測試

【請求URL】:http://192.168.1.7:27100/user/updateUserInfo
【請求方式】:POST
【請求參數(shù)】:
{
  "id":1,
  "userName":"李四"
}
 
【執(zhí)行結(jié)果】:
id:1,userName:李四,更新成功

【注】入?yún)⒅袥]有傳“密碼”,也沒有校驗(yàn),若默認(rèn)屬于 Default 分組的字段也需要校驗(yàn),可以寫成:

public String updateUserInfo(@RequestBody @Validated({Update.class, Default.class}) User user) {

場景四:級聯(lián)校驗(yàn)

1、在實(shí)體類模型中,可能會存在集合類型或?qū)嶓w類型的成員變量,該成員中的字段仍然需要校驗(yàn)。

在要校驗(yàn)的對象類型的屬性/ list上使用 @Valid 注解:

@Data
public class User {
    @NotNull(message = "更新數(shù)據(jù)時(shí),主鍵id不能為空", groups = Update.class)
    private Integer id;
    @NotEmpty(message = "用戶名不能為空")
    private String userName;
    private Integer age;
    @NotNull(message = "用戶密碼不能為空")
    @Size(min = 5, max = 10,message = "密碼長度必須是5-10個(gè)字符")
    private String password;
    @Valid
    private List<Car> cars;
}
@Data
public class Car {
    @NotNull(message = "車牌號碼不能為空")
    private String plateCode; 
    @NotNull(message = "車牌顏色不能為空")
    private String plateColor;
}

2、處理器方法

@Validated
@RestController
@RequestMapping("/user")
public class UserController {
    @PostMapping("/saveUserInfo")
    public String saveUserInfo(@RequestBody @Validated User user) {
        System.out.println("userName:"+ user.getUserName() +",保存成功");
        return "success";
    }
}

3、測試

【請求URL】:http://192.168.1.7:27100/user/saveUserInfo
【請求方式】:POST
【請求參數(shù)】:
{
    "userName": "李四",
    "password": "123456",
    "cars": [
        {
            "plateCode": "京A0001",
            "plateColor": "1"
        },
                {
            "plateCode": "京A0002"
        }
    ]
}
【執(zhí)行結(jié)果】:
{
     "code": 2,
     "message": "非法參數(shù)",
     "data": "車牌顏色不能為空"
}

場景五:自定義注釋校驗(yàn)

如下:校驗(yàn)用戶下車牌號碼必須包含“京A”,否則返回提示;

1、自定義注釋

@Target({METHOD, FIELD, ANNOTATION_TYPE, CONSTRUCTOR, PARAMETER})
@Retention(RUNTIME)
@Documented
@Constraint(validatedBy = {MustContainKeyValidator.class})
public @interface MustContainKey {
    //默認(rèn)錯(cuò)誤信息
    String message() default "必須含有指定關(guān)鍵字";
   //分組
    Class<?>[] groups() default {};
    // 負(fù)載
    Class<? extends Payload>[] payload() default {};
}

2、真正的校驗(yàn)者類,實(shí)現(xiàn) ConstraintValidator 接口

public class MustContainKeyValidator implements ConstraintValidator<MustContainKey,String> {
    @Override
    public boolean isValid(String value, ConstraintValidatorContext context) {
        if (!StringUtils.isEmpty(value) && !value.contains("京A")) {
            // 獲取默認(rèn)提示消息
            String defaultConstraintMessageTemplate = context.getDefaultConstraintMessageTemplate();
            System.out.println(defaultConstraintMessageTemplate);
            // 禁用默認(rèn)提示信息
            // context.disableDefaultConstraintViolation();
            //設(shè)置提示語
            // context.buildConstraintViolationWithTemplate("must contain key").addConstraintViolation();
            return false;
        }
        return true;
    }
}

3、在實(shí)體類的屬性上添加該注釋

@Data
public class User {
    @NotNull(message = "更新數(shù)據(jù)時(shí),主鍵id不能為空", groups = Update.class)
    private Integer id;
    @NotEmpty(message = "用戶名不能為空")
    private String userName;
    private Integer age;
    @NotNull(message = "用戶密碼不能為空")
    @Size(min = 5, max = 10,message = "密碼長度必須是5-10個(gè)字符")
    private String password;
    @Valid
    private List<Car> cars;
}
@Data
public class Car {
    @MustContainKey
    @NotNull(message = "車牌號碼不能為空")
    private String plateCode; 
    @NotNull(message = "車牌顏色不能為空")
    private String plateColor;
}

4、測試

【請求URL】:http://192.168.1.7:27100/user/saveUserInfo
【請求方式】:POST
【請求參數(shù)】:
{
        
    "userName": "李四",
    "password": "123456",
    "cars": [
        {
            "plateCode": "京A0001",
            "plateColor": "1"
        },
        {
            "plateCode": "浙C0002",
            "plateColor": "2"
        }
    ]
}
【執(zhí)行結(jié)果】:
{
     "code": 2,
     "message": "非法參數(shù)",
     "data": "必須含有指定關(guān)鍵字"
}

以上就是所有關(guān)于 Spring Validation 的介紹!

總結(jié)

到此這篇關(guān)于Spring Validation接口入?yún)⑿r?yàn)的文章就介紹到這了,更多相關(guān)Spring Validation接口入?yún)⑿r?yàn)內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • Java事故排查過程詳細(xì)講解

    Java事故排查過程詳細(xì)講解

    Java線上問題排查是一個(gè)復(fù)雜但重要的過程,涉及多個(gè)方面,這篇文章主要介紹了Java事故排查過程的相關(guān)資料,文中通過代碼介紹的非常詳細(xì),需要的朋友可以參考下
    2025-10-10
  • 關(guān)于Java JDK安裝、配置環(huán)境變量的問題

    關(guān)于Java JDK安裝、配置環(huán)境變量的問題

    這篇文章主要介紹了Java JDK安裝、配置環(huán)境變量,本文給大家介紹的非常詳細(xì),對大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下
    2021-03-03
  • Java面向?qū)ο笾畠?nèi)部類詳解

    Java面向?qū)ο笾畠?nèi)部類詳解

    在 Java 中,允許一個(gè)類的定義位于另一個(gè)類的內(nèi)部,前者稱為內(nèi)部類,后者稱為外部類。這篇文章將總結(jié)一下內(nèi)部類的使用,感興趣的可以了解一下
    2022-10-10
  • springboot+vue實(shí)現(xiàn)海康攝像頭喊話功能的完整方案

    springboot+vue實(shí)現(xiàn)海康攝像頭喊話功能的完整方案

    這兩天因工作原因,需要對??低晹z像頭進(jìn)行二次開發(fā),這篇文章主要介紹了springboot+vue實(shí)現(xiàn)??禂z像頭喊話功能的完整方案,文中通過代碼介紹的非常詳細(xì),需要的朋友可以參考下
    2026-03-03
  • SpringCloud版本問題報(bào)錯(cuò)及解決方法

    SpringCloud版本問題報(bào)錯(cuò)及解決方法

    這篇文章主要介紹了SpringCloud版本問題報(bào)錯(cuò)及解決方法,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下
    2019-07-07
  • Spring Boot 配置文件深度解析

    Spring Boot 配置文件深度解析

    本文深入探討SpringBoot配置文件的使用技巧,對比Properties與YAML格式優(yōu)缺點(diǎn),實(shí)戰(zhàn)@Value與@ConfigurationProperties注解讀取配置,并通過驗(yàn)證碼案例演示配置集成方法,感興趣的朋友跟隨小編一起看看吧
    2026-06-06
  • Java顯示程序包不存在的三種解決方法總結(jié)

    Java顯示程序包不存在的三種解決方法總結(jié)

    在Java開發(fā)中,有時(shí)會遇到“程序包javax.servlet不存在”等錯(cuò)誤提示,這通常是因?yàn)槿鄙俦匾膸旎蛞蕾図?xiàng),這篇文章主要給大家介紹了關(guān)于Java顯示程序包不存在的三種解決方法,需要的朋友可以參考下
    2024-07-07
  • Java網(wǎng)絡(luò)編程之URL+URLconnection使用方法示例

    Java網(wǎng)絡(luò)編程之URL+URLconnection使用方法示例

    這篇文章主要介紹了Java網(wǎng)絡(luò)編程之URL+URLconnection使用方法示例,還是比較不錯(cuò)的,這里分享給大家,供需要的朋友參考。
    2017-11-11
  • 深入解析Java的Servlet過濾器的原理及其應(yīng)用

    深入解析Java的Servlet過濾器的原理及其應(yīng)用

    這篇文章主要介紹了深入解析Java的Servlet過濾器的原理及應(yīng)用,Java編寫的Servlet通常是一個(gè)與網(wǎng)頁一起作用于瀏覽器客戶端的程序,需要的朋友可以參考下
    2016-01-01
  • Mybatis-Plus 條件構(gòu)造器 QueryWrapper 的基本用法

    Mybatis-Plus 條件構(gòu)造器 QueryWrapper 的基本用法

    這篇文章主要介紹了Mybatis-Plus - 條件構(gòu)造器 QueryWrapper 的使用,通過實(shí)例代碼給大家介紹了查詢示例代碼及實(shí)現(xiàn)需求,代碼簡單易懂,對大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下
    2021-09-09

最新評論

镇康县| 航空| 岑溪市| 桐乡市| 高雄市| 贵定县| 利津县| 司法| 大足县| 锡林浩特市| 涟水县| 德钦县| 利辛县| 全南县| 中超| 古丈县| 武威市| 曲沃县| 额济纳旗| 金乡县| 凉山| 邓州市| 岐山县| 金平| 饶河县| 山东省| 抚州市| 阳城县| 法库县| 山阳县| 错那县| 理塘县| 海伦市| 临洮县| 吉水县| 平乡县| 新巴尔虎左旗| 延津县| 宁德市| 图们市| 阿拉善盟|