Java參數(shù)校驗(yàn)Validator與@AssertTrue深度解析
Java參數(shù)校驗(yàn)最佳實(shí)踐:Validator與@AssertTrue深度解析
1. 引言
在企業(yè)級(jí)應(yīng)用開(kāi)發(fā)中,參數(shù)校驗(yàn)是保證數(shù)據(jù)質(zhì)量的第一道防線。本文將深入介紹Java的Validator框架的使用,特別是如何結(jié)合@AssertTrue注解實(shí)現(xiàn)復(fù)雜的業(yè)務(wù)校驗(yàn)邏輯。
2. 環(huán)境準(zhǔn)備
2.1 依賴(lài)配置
<dependency>
<groupId>javax.validation</groupId>
<artifactId>validation-api</artifactId>
<version>2.0.1.Final</version>
</dependency>
<dependency>
<groupId>org.hibernate.validator</groupId>
<artifactId>hibernate-validator</artifactId>
<version>6.1.5.Final</version>
</dependency>3. 基礎(chǔ)注解介紹
常用的校驗(yàn)注解包括:
@NotBlank: 字符串不能為null且去除空格后長(zhǎng)度必須大于0@Pattern: 通過(guò)正則表達(dá)式校驗(yàn)字符串格式@Size: 校驗(yàn)字符串、集合、數(shù)組等的長(zhǎng)度范圍@AssertTrue: 校驗(yàn)方法返回值必須為true@NotNull: 不能為null@Min: 數(shù)值必須大于等于指定值@Max: 數(shù)值必須小于等于指定值@Email: 校驗(yàn)郵箱格式
4. 實(shí)戰(zhàn)示例
4.1 請(qǐng)求對(duì)象定義
@Data
public class ImageRequest {
/**
* 圖片URL地址
*/
@Pattern(regexp = "^(http|https)://.*", message = "圖片URL格式不正確")
@Size(max = 1024, message = "圖片URL長(zhǎng)度不能超過(guò)1024個(gè)字符")
private String imageUrl;
/**
* Base64編碼的圖片數(shù)據(jù)
*/
@Size(max = 10 * 1024 * 1024, message = "Base64圖片數(shù)據(jù)不能超過(guò)10MB")
private String base64Image;
/**
* 設(shè)備編號(hào)
*/
@NotBlank(message = "設(shè)備編號(hào)不能為空")
private String deviceNo;
/**
* 用戶標(biāo)識(shí)
*/
@NotBlank(message = "用戶標(biāo)識(shí)不能為空")
private String userId;
/**
* 自定義校驗(yàn)方法:確保至少提供一種圖片數(shù)據(jù)
*/
@AssertTrue(message = "必須提供圖片URL或Base64編碼圖片數(shù)據(jù)其中之一")
public boolean isImageDataValid() {
return StringUtils.isNotBlank(imageUrl) || StringUtils.isNotBlank(base64Image);
}
}4.2 校驗(yàn)實(shí)現(xiàn)
public class ValidationExample {
private final Validator validator;
public ValidationExample() {
ValidatorFactory factory = Validation.buildDefaultValidatorFactory();
this.validator = factory.getValidator();
}
public void validateRequest(ImageRequest request) {
// 執(zhí)行校驗(yàn)
Set<ConstraintViolation<ImageRequest>> violations = validator.validate(request);
// 如果存在校驗(yàn)錯(cuò)誤
if (!violations.isEmpty()) {
// 收集所有驗(yàn)證錯(cuò)誤信息
String errorMessage = violations.stream()
.map(ConstraintViolation::getMessage)
.collect(Collectors.joining("; "));
log.error("參數(shù)校驗(yàn)失敗:{}", errorMessage);
throw new IllegalArgumentException("參數(shù)校驗(yàn)失?。? + errorMessage);
}
}
}5. @AssertTrue深入解析
5.1 基本用法
@AssertTrue注解用于復(fù)雜的業(yè)務(wù)校驗(yàn)場(chǎng)景,特別是涉及多個(gè)字段之間的關(guān)聯(lián)校驗(yàn)時(shí)。
5.2 命名規(guī)范
@AssertTrue(message = "校驗(yàn)失敗的提示信息")
public boolean isXxxValid() {
// 校驗(yàn)邏輯
return true/false;
}5.3 常見(jiàn)使用場(chǎng)景
5.3.1 互斥字段校驗(yàn)
@AssertTrue(message = "付款方式只能選擇其中一種")
public boolean isPaymentMethodValid() {
return (alipay != null) ^ (wechatPay != null);
}5.3.2 依賴(lài)字段校驗(yàn)
@AssertTrue(message = "當(dāng)選擇快遞配送時(shí),收貨地址不能為空")
public boolean isDeliveryAddressValid() {
return !DeliveryType.EXPRESS.equals(deliveryType) ||
StringUtils.isNotBlank(deliveryAddress);
}5.3.3 數(shù)值范圍聯(lián)動(dòng)校驗(yàn)
@AssertTrue(message = "結(jié)束時(shí)間必須晚于開(kāi)始時(shí)間")
public boolean isTimeRangeValid() {
return endTime != null && startTime != null &&
endTime.after(startTime);
}6. 高級(jí)特性
6.1 分組校驗(yàn)
public interface Create {}
public interface Update {}
@AssertTrue(message = "創(chuàng)建時(shí)的校驗(yàn)規(guī)則", groups = {Create.class})
public boolean isCreateValid() {
return ...;
}
@AssertTrue(message = "更新時(shí)的校驗(yàn)規(guī)則", groups = {Update.class})
public boolean isUpdateValid() {
return ...;
}6.2 組合校驗(yàn)規(guī)則
@AssertTrue(message = "圖片數(shù)據(jù)格式校驗(yàn)失敗")
public boolean isImageFormatValid() {
if (StringUtils.isNotBlank(imageUrl)) {
return imageUrl.startsWith("http") &&
(imageUrl.endsWith(".jpg") || imageUrl.endsWith(".png"));
}
if (StringUtils.isNotBlank(base64Image)) {
return base64Image.startsWith("data:image/");
}
return false;
}7. 最佳實(shí)踐建議
統(tǒng)一異常處理
- 創(chuàng)建全局異常處理器
- 統(tǒng)一校驗(yàn)失敗的返回格式
性能優(yōu)化
- ValidatorFactory應(yīng)該是單例的
- 避免在校驗(yàn)方法中進(jìn)行重量級(jí)操作
代碼規(guī)范
- 校驗(yàn)方法命名要規(guī)范且具有描述性
- 保持校驗(yàn)邏輯的簡(jiǎn)單清晰
且具有描述性保持校驗(yàn)邏輯的簡(jiǎn)單清晰
測(cè)試覆蓋
- 編寫(xiě)完整的單元測(cè)試
- 覆蓋各種邊界條件
文檔維護(hù)
- 記錄校驗(yàn)規(guī)則的業(yè)務(wù)含義
- 及時(shí)更新文檔
到此這篇關(guān)于Java參數(shù)校驗(yàn)Validator與@AssertTrue深度解析的文章就介紹到這了,更多相關(guān)java參數(shù)校驗(yàn)Validator與@AssertTrue內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
JAVA PDF操作之實(shí)現(xiàn)截取N頁(yè)和多個(gè)PDF合并
這篇文章主要為大家詳細(xì)介紹了java關(guān)于PDF的一些操作,例如截取N頁(yè)并生成新文件,轉(zhuǎn)圖片以及多個(gè)PDF合并,文中的示例代碼講解詳細(xì),感興趣的可以了解下2025-01-01
Spring擴(kuò)展BeanFactoryPostProcessor使用技巧詳解
這篇文章主要為大家介紹了Spring擴(kuò)展BeanFactoryPostProcessor使用技巧詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2022-09-09
java實(shí)現(xiàn)在SSM下使用支付寶掃碼支付功能
這篇文章主要為大家詳細(xì)介紹了java實(shí)現(xiàn)在SSM下使用支付寶掃碼支付功能,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2018-02-02
feign調(diào)用返回object類(lèi)型轉(zhuǎn)換方式
這篇文章主要介紹了feign調(diào)用返回object類(lèi)型轉(zhuǎn)換方式,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2021-06-06

