亚洲乱码中文字幕综合,中国熟女仑乱hd,亚洲精品乱拍国产一区二区三区,一本大道卡一卡二卡三乱码全集资源,又粗又黄又硬又爽的免费视频

利用Spring Validation實現(xiàn)輸入驗證功能

 更新時間:2023年06月18日 14:42:41   作者:半畝方塘立身  
這篇文章主要給大家介紹了如何利用Spring Validation完美的實現(xiàn)輸入驗證功能,文中有詳細的代碼示例,具有一定的參考價值,感興趣的朋友可以借鑒一下

概述

校驗例子

大家平時編碼中經(jīng)常涉及參數(shù)的校驗,對于一個用戶注冊的方法來說會校驗用戶名密碼信息:

public class UserController {
    public ResponseEntity<String> registerUser(String username, String password) {
        if (username == null || username.isEmpty()) {
            return ResponseEntity.badRequest().body("用戶名不能為空");
        }
        if (password == null || password.isEmpty()) {
            return ResponseEntity.badRequest().body("密碼不能為空");
        }
        if (password.length() < 6) {
            return ResponseEntity.badRequest().body("密碼長度至少為6位");
        }
        // 處理用戶注冊邏輯
        return ResponseEntity.ok("用戶注冊成功");
    }
}

上述例子中需要手動編寫參數(shù)校驗邏輯的過程。雖然對于這個簡單的示例而言,手動編寫校驗邏輯可能是可行的,但是對于復雜的驗證規(guī)則和多個參數(shù)的情況,手動編寫校驗邏輯會變得冗長、難以維護和復用。

引入現(xiàn)代的校驗框架如Spring Validation可以幫助解決這些問題,提供更高效、統(tǒng)一和可維護的參數(shù)校驗方案。

Bean Validation規(guī)范

  • JSR303/JSR-349/JSR-380: JSR303(Bean Validation)是一項標準,只提供規(guī)范不提供實現(xiàn),規(guī)定一些校驗規(guī)范即校驗注解,如@Null,@NotNull,@Pattern,位于javax.validation.constraints包下。JSR-349(Bean Validation 1.1)是其的升級版本,添加了一些新特性。JSR-380(Bean Validation 2.0,JSR380標準 )對其規(guī)范進一步擴展和增強。
  • hibernate validationhibernate validation是對這個規(guī)范的實現(xiàn),并增加了一些其他校驗注解,如@Email,@Length,@Range等等
  • Spring validationspring validationhibernate validation進行了二次封裝,在springmvc模塊中添加了自動校驗,并將校驗信息封裝進了特定的類中

Bean Validation的主頁:Jakarta Bean Validation - Home

Bean Validation的參考實現(xiàn):GitHub - hibernate/hibernate-validator: Hibernate Validator - Jakarta Bean Validation Reference Implementation

相關版本兼容性

Bean ValidationHibernate ValidationJDKSpring Boot
1.15.4 +6+1.5.x
2.06.0 +8+2.0.x
3.07.0 +9+2.0.x

3.0后Bean Validation改名為Jakarta Bean Validation 3.0了。 如果你的項目版本是jdk1.8的,不要使用hibernate-validator 7.0的版本,它里面的依賴的jakarta.validation-api:3.0是需要jdk1.9的部分支持的。

Spring Validation注解

Spring Validation建立在Java Bean Validation(JSR 380)的基礎上,為開發(fā)人員提供了一組注解和工具,用于定義和執(zhí)行數(shù)據(jù)驗證規(guī)則。它允許開發(fā)人員在應用程序中定義驗證規(guī)則,并使用這些規(guī)則來驗證輸入數(shù)據(jù)、請求參數(shù)、領域對象等。

@Validated:可以用在類型、方法和方法參數(shù)上。但是不能用在成員屬性(字段)上

@Valid:可以用在方法、構造函數(shù)、方法參數(shù)和成員屬性(字段)上

常用注解標簽如下:

標簽說明
@Null限制只能為null
@NotNull限制必須不為null
@AssertFalse限制必須為false
@AssertTrue限制必須為true
@DecimalMax(value)限制必須為一個不大于指定值的數(shù)字
@DecimalMin(value)限制必須為一個不小于指定值的數(shù)字
@Digits(integer,fraction)限制必須為一個小數(shù),且整數(shù)部分的位數(shù)不能超過integer,小數(shù)部分的位數(shù)不能超過fraction
@Future限制必須是一個將來的日期
@Max(value)限制必須為一個不大于指定值的數(shù)字
@Min(value)限制必須為一個不小于指定值的數(shù)字
@Past限制必須是一個過去的日期
@Pattern(value)限制必須符合指定的正則表達式
@Size(max,min)限制字符長度必須在min到max之間
@Past驗證注解的元素值(日期類型)比當前時間早
@NotEmpty驗證注解的元素值不為null且不為空(字符串長度不為0、集合大小不為0)
@NotBlank驗證注解的元素值不為空(不為null、去除首位空格后長度為0),不同于@NotEmpty,@NotBlank只應用于字符串且在比較時會去除字符串的空格
@Email驗證注解的元素值是Email,也可以通過正則表達式和flag指定自定義的email格式

hibernate-validator 校驗Java Bean

  • pom引入hibernate-validator
<dependency>
    <groupId>org.hibernate.validator</groupId>
    <artifactId>hibernate-validator</artifactId>
    <version>6.2.0.Final</version>
</dependency>
  • 創(chuàng)建一個Java Bean,我們校驗一下用戶名跟年齡
public class User {
    @NotBlank(message = "用戶名不能為空")
    private String username;
    @Min(value = 18, message = "年齡不能小于18歲")
    private int age;
    // 構造函數(shù)、Getter 和 Setter 方法
}
  • 執(zhí)行校驗
public class ValidatorTest {
    public static void main(String[] args) {
        // 創(chuàng)建校驗器
        ValidatorFactory factory = Validation.buildDefaultValidatorFactory();
        Validator validator = factory.getValidator();
        // 創(chuàng)建用戶對象
        User user = new User();
        user.setUsername("");
        user.setAge(16);
        // 執(zhí)行校驗
        Set<ConstraintViolation<User>> violations = validator.validate(user);
        // 處理校驗結果
        if (!violations.isEmpty()) {
            for (ConstraintViolation<User> violation : violations) {
                System.out.println(violation.getMessage());
            }
        } else {
            System.out.println("校驗通過");
        }
    }
}

用Spring Validation提高生產(chǎn)力

Spring Validation引入

添加pom依賴

Spring Validation校驗包被獨立成了一個starter組件,引入如下依賴:

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-validation</artifactId>
</dependency>

如果是spring-boot-starter-web不用引入了,spring-boot-starter-web 集成了spring-boot-starter-validation,默認可以不加spring-boot-starter-validation,它同時也集成了hibernate-validator

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-web</artifactId>
</dependency>

hibernate Validator校驗器

這里我們定義hibernate校驗器用于校驗參數(shù)

@Configuration
@EnableAutoConfiguration
public class HibernateValidatorConfiguration {
	@Bean
	public MethodValidationPostProcessor methodValidationPostProcessor() {
		MethodValidationPostProcessor processor = new MethodValidationPostProcessor();
		processor.setValidator(validator());
		processor.setProxyTargetClass(true);
		return processor;
	}
	@Bean
	public Validator validator() {
		return Validation
				.byProvider(HibernateValidator.class)
				.configure()
				.addProperty("hibernate.validator.fail_fast", "true")
				.buildValidatorFactory()
				.getValidator();
	}
}

全局異常處理

每個Controller方法中都如果都寫一遍對校驗結果信息的處理,使用起來還是很繁瑣??梢酝ㄟ^全局異常處理的方式統(tǒng)一處理校驗異常。

@ControllerAdvice
@Slf4j
public class GlobalExceptionHandler {
    @ExceptionHandler(value = ConstraintViolationException.class)
	@ResponseBody
	public ApiResult defaultInsuranceExceptionHandler(ConstraintViolationException e) {
		log.error("校驗錯誤:{}", e.getMessage());
		return ApiResult.error("error", e.getMessage());
	}
	@ExceptionHandler(value = MissingServletRequestParameterException.class)
	@ResponseBody
	public ApiResult handleMissingServletRequestParameter(MissingServletRequestParameterException ex) {
		String error = ex.getParameterName() + " 參數(shù)為空";
		return ApiResult.error("error", error);
	}
}

Controller接口Bean校驗

首先,假設我們有一個用戶注冊的請求對象 UserRegistrationRequest,其中包含用戶名和密碼字段。

@Data
public class UserRegistrationRequest {
    @NotBlank(message = "用戶名不能為空")
    private String username;
    @NotBlank(message = "密碼不能為空")
    @Size(min = 6, message = "密碼長度至少為6位")
    private String password;
}

我們使用了兩個注解進行參數(shù)校驗:

  • @NotBlank:該注解用于驗證字段不能為空或空格,并可以通過 message 屬性指定驗證失敗時的錯誤消息。
  • @Size:該注解用于驗證字段的長度,我們指定了密碼的最小長度為6,并通過 message 屬性定義了驗證失敗時的錯誤消息。

接下來我們定義一個Controller接口

@RestController
public class UserController {
    @PostMapping("/register")
    public ResponseEntity<String> registerUser(@Valid @RequestBody UserRegistrationRequest request) {
        // 處理用戶注冊邏輯
        return ResponseEntity.ok("用戶注冊成功");
    }
}

@RequestParam 參數(shù)校驗

首先需要將MethodValidationPostProcessor設置成cglib代理

processor.setProxyTargetClass(true);

controller實現(xiàn)

@RestController
public class ValidController implements ValidClient {
	@Override
	public String queryById(Integer id) {
		return "id:" + id;
	}
}

分組校驗

還是看上面那個Controller接口校驗的例子,如果我們注冊的時候需要校驗用戶名和密碼,重置密碼的時候只校驗密碼該怎么校驗呢?這個時候就用到了分組校驗了。

  • 首先,我們需要定義一個新的分組,用于更新場景中的驗證,例如UpdateGroup
public interface UpdateGroup {
}

  • 接下來,我們需要在UserRegistrationRequest類的username字段上使用@Validated注解,并通過groups屬性指定要應用的驗證分組。
public class UserRegistrationRequest {
    @NotBlank(message = "用戶名不能為空", groups = {RegistrationGroup.class})
    private String username;
    @NotBlank(message = "密碼不能為空")
    @Size(min = 6, message = "密碼長度至少為6位")
    private String password;
    // 其他字段和方法
}

在上述示例中,我們將@Validated注解應用到username字段,并通過groups屬性指定了RegistrationGroup.class,這意味著在注冊場景中會進行校驗。

  • 我們可以使用@Validated注解來指定不要應用任何驗證分組。
@RestController
public class UserController {
    @PostMapping("/register")
    public ResponseEntity<String> registerUser(@Validated(RegistrationGroup.class) @RequestBody UserRegistrationRequest request) {
        // 處理用戶注冊邏輯
        return ResponseEntity.ok("用戶注冊成功");
    }
    @PostMapping("/update")
    public ResponseEntity<String> updateUser(@Validated(UpdateGroup.class) @RequestBody UserRegistrationRequest request) {
        // 處理用戶更新邏輯
        return ResponseEntity.ok("用戶更新成功");
    }
}

在上述示例中,我們在updateUser方法中使用@Validated(UpdateGroup.class)來指定在更新場景中只執(zhí)行UpdateGroup分組的驗證規(guī)則。由于username字段上沒有指定groups屬性,所以在更新場景中將不會對username字段進行校驗。

自定義注解

Spring 的 validation 為我們提供了許多特性,幾乎可以滿足日常開發(fā)中絕大多數(shù)參數(shù)校驗場景了。但是,一個好的框架一定是方便擴展的。有了擴展能力,就能應對更多復雜的業(yè)務場景,下面我們自定義一個日期格式校驗的注解

定義注解接口

@Documented
@Constraint(validatedBy = DateFormatValidator.class)
@Target({ElementType.METHOD, ElementType.FIELD, ElementType.ANNOTATION_TYPE, ElementType.CONSTRUCTOR, ElementType.PARAMETER, ElementType.TYPE_USE})
@Retention(RetentionPolicy.RUNTIME)
public @interface DateFormat {
	//默認錯誤消息
	String message() default "時間格式錯誤";
	//分組
	Class<?>[] groups() default {};
	//默認日期格式
	String formatter() default "yyyy-MM-dd";
	//負載
	Class<? extends Payload>[] payload() default {};
	@Target({ElementType.METHOD, ElementType.FIELD, ElementType.ANNOTATION_TYPE, ElementType.CONSTRUCTOR, ElementType.PARAMETER, ElementType.TYPE_USE})
	@Retention(RetentionPolicy.RUNTIME)
	@Documented
	@interface List {
		DateFormat[] value();
	}
}

定義校驗器

public class DateFormatValidator implements ConstraintValidator<DateFormat, String> {
	protected String dateFormatter;
	@Override
	public void initialize(DateFormat constraintAnnotation) {
		this.dateFormatter = constraintAnnotation.formatter();
	}
	@Override
	public boolean isValid(String value, ConstraintValidatorContext constraintValidatorContext) {
		if (StringUtils.isNotBlank(value)) {
			try {
				DateUtils.parseDate(value, dateFormatter);
			} catch (Exception e) {
				return false;
			}
			return true;
		}
		return false;
	}
}

自定義校驗注解使用起來和官方注解沒有區(qū)別,在需要的字段上添加相應注解即可。

public class RequestParam {
    @DateFormat(message = "日期輸入錯誤")
    private String beginDate;
    // 其他字段和方法
}

以上就是利用Spring Validation實現(xiàn)輸入驗證功能的詳細內(nèi)容,更多關于Spring Validation輸入驗證的資料請關注腳本之家其它相關文章!

相關文章

  • SpringBoot 如何讀取pom.xml中的值

    SpringBoot 如何讀取pom.xml中的值

    這篇文章主要介紹了SpringBoot 如何讀取pom.xml中的值,具有很好的參考價值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教
    2022-01-01
  • 解決微服務中關于用戶token處理到的坑

    解決微服務中關于用戶token處理到的坑

    這篇文章主要介紹了解決微服務中關于用戶token處理到的坑,具有很好的參考價值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教
    2021-08-08
  • 23種設計模式(15)java解釋器模式

    23種設計模式(15)java解釋器模式

    這篇文章主要為大家詳細介紹了23種設計模式之java解釋器模式,具有一定的參考價值,感興趣的小伙伴們可以參考一下
    2017-12-12
  • SpringBoot Tomcat啟動實例代碼詳解

    SpringBoot Tomcat啟動實例代碼詳解

    這篇文章主要介紹了SpringBoot Tomcat啟動實例代碼詳解,需要的朋友可以參考下
    2017-09-09
  • 關于使用swagger整合springMVC的方法

    關于使用swagger整合springMVC的方法

    在平時開發(fā)寫接口文檔的工作時,一般都是word文檔,帶來書寫麻煩、維護麻煩的問題,比如改了源代碼忘了更新文檔、解釋不明確帶來歧義、無法在線嘗試等等,swagger可以有效解決這類問題,需要的朋友可以參考下
    2023-04-04
  • java條件語句示例詳解

    java條件語句示例詳解

    本文給大家介紹java條件語句,Java 中的條件語句允許程序根據(jù)條件的不同執(zhí)行不同的代碼塊,一個 if 語句包含一個布爾表達式和一條或多條語句,本文結合示例代碼給大家講解的非常詳細,需要的朋友可以參考下
    2023-05-05
  • 詳解Spring Data JPA中Repository的接口查詢方法

    詳解Spring Data JPA中Repository的接口查詢方法

    repository代理有兩種方式從方法名中派生出特定存儲查詢:通過直接從方法名派生查詢和通過使用一個手動定義的查詢。本文將通過示例詳細講解Spring Data JPA中Repository的接口查詢方法,需要的可以參考一下
    2022-04-04
  • JPA save()方法將字段更新為null的解決方案

    JPA save()方法將字段更新為null的解決方案

    這篇文章主要介紹了JPA save()方法將字段更新為null的解決方案,文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友可以參考下
    2020-01-01
  • java中@JSONField和@JsonProperty注解的使用說明及對比

    java中@JSONField和@JsonProperty注解的使用說明及對比

    @JSONField與@JsonProperty隸屬兩個不同的包,前者是阿里系的fastjson包,后者是spring?boot官方使用的jackson包,本文主要介紹了java中@JSONField和@JsonProperty注解的使用說明及對比,感興趣的可以了解一下
    2023-11-11
  • java獲取登錄者IP和登錄時間的兩種實現(xiàn)代碼詳解

    java獲取登錄者IP和登錄時間的兩種實現(xiàn)代碼詳解

    這篇文章主要介紹了java獲取登錄者IP和登錄時間的實現(xiàn)代碼,本文通過兩種結合實例代碼給大家介紹的非常詳細,對大家的學習或工作具有一定的參考借鑒價值,需要的朋友可以參考下
    2020-07-07

最新評論