当前位置:网站首页>數據驗證框架 Apache BVal 再使用
數據驗證框架 Apache BVal 再使用
2022-07-07 18:54:00 【sp42a】
關於 Apache BVal,我 N 久之前使用過,還寫了甚至全網唯一的簡中教程《數據驗證框架 Apache BVal 簡介》,我依然還是那個觀點:
Apache BVal (源碼)是實體數據驗證 Java Bean Validation 的參考實現。Apache BVal 提供了 JSR 303 規範中所有內置 constraint 的實現,用於對 Bean 中的字段的值進行約束定義、描述和驗證。若單單說 JSR 規範大渣可能還不清楚,但做過 POJO 的 Hibernate Validator 注解的朋友就知道是啥,——那為什麼不使用主流的 Hibernate Validator 呢?因為這貨淨是個壓縮包都已經 13mb 了(盡管可以有文檔、源碼其他在內),BVal 才只有 400 多 kb,而我只需要服務端驗證而已,——天真的孩紙傷不起啊。俺的 ORM 也是 Mybatis 的,務求盡可能地輕量級。
用法
Maven 引用
添加以下兩個 Maven 依賴:
<dependency>
<groupId>org.apache.bval</groupId>
<artifactId>bval-jsr</artifactId>
<version>2.0.6</version>
</dependency>
<dependency>
<groupId>javax.validation</groupId>
<artifactId>validation-api</artifactId>
<version>2.0.1.Final</version>
</dependency>
2.0 要求 Java 8,Apache CommonUtils 不是强依賴了,同時 JSR 驗證規範也昇級到 2.x。
整合 Spring
Spring 裏面注入 Provider。
/** * 數據驗證框架 * * @return */
@Bean
LocalValidatorFactoryBean localValidatorFactoryBean() {
LocalValidatorFactoryBean v = new LocalValidatorFactoryBean();
v.setProviderClass(ApacheValidationProvider.class);
return v;
}
調用校驗
手動校驗方法,先試試
@Autowired
LocalValidatorFactoryBean v;
public List<DataDict> getDataDict(Long parentId) {
List<DataDict> list = DataDictDao.DataDictDAO.setWhereQuery("parentId", parentId).findList();
Validator validator = v.getValidator();
Set<ConstraintViolation<DataDict>> violations = validator.validate(list.get(0));
System.out.println(violations.size()); // 校驗結果
System.out.println(list.get(0).getParentId());
if (CollectionUtils.isEmpty(list))
list = new ArrayList<>();
return list;
}
上述代碼是對一個 Java Bean:DataDict 進行校驗,Bean 的字段可配置如下的約束。
public class DataDict implements CommonEntity {
/** * 主鍵 id,自增 */
private Long id;
/** * 父 id */
@NotNull
private Long parentId;
/** * 類型 id */
@NotNull
private Long type;
……
}
更多校驗注解參見舊文。
Spring MVC 自動校驗
很簡單,添加注解 @Valid
在 Bean 參數上。
/** * 新建 * @return */
@RequestMapping(method = RequestMethod.POST)
public String create(@Valid T news, Model model) {
System.out.println("新建");
if (result.hasErrors()) {
LOGGER.info("create error!");
}else{
LOGGER.info("create ok!");
}
news.setService(getService());
try {
getService().create(news);
model.addAttribute("newlyId", news.getId());
} catch (ServiceException e) {
model.addAttribute("errMsg", e.toString());
}
return "common/entity/json_cud";
}
接著說說怎麼處理錯誤,或者不處理默認交由 Servlet 處理也可以。下面是自定義异常的處理器,轉化為 JSON 返回。
import java.util.List;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.springframework.validation.BindException;
import org.springframework.validation.FieldError;
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;
import com.ajaxjs.util.WebHelper;
/** * 後端錶單、數據校驗的异常捕獲 * * @author Frank Cheung<[email protected]> * */
@ControllerAdvice
public class RestResponseEntityExceptionHandler {
static final String TPL = "輸入字段 [%s] 未通過校驗,原因 [%s],輸入值為 [%s],請檢查後再提交。";
@ExceptionHandler(value = BindException.class)
public void exceptionHandler(HttpServletRequest req, HttpServletResponse resp, BindException e) {
String msg = "";
List<FieldError> fieldErrors = e.getBindingResult().getFieldErrors();
for (FieldError err : fieldErrors) {
msg += String.format(TPL, err.getField(), err.getDefaultMessage(), err.getRejectedValue());
// msg += "\\\\n";
}
ResponseResult result = new ResponseResult();
result.setErrorCode("400");
result.setMessage(msg);
WebHelper.outputJson(resp, result.toString());
}
}
這個 RestResponseEntityExceptionHandler 按照正常注入 Spring 組件方式即可,下面是一種方法:
@Bean
RestResponseEntityExceptionHandler initRestResponseEntityExceptionHandler() {
return new RestResponseEntityExceptionHandler();
}
JSR 303 可以自定義約束的原因,這樣就不會輸出默認的英文,但要逐個說明也比較麻煩。
另外有個 getAllErrors,這個不是針對字段的,估計是 for 校驗方法的。
List<ObjectError> allErrors = e.getAllErrors();
for (ObjectError err : allErrors) {
msg += err.getDefaultMessage();
msg += StringUtils.arrayToDelimitedString(err.getCodes(), ",");
}
高級用法
Apache BVal 的功能還遠不止這些,可以參考老外的文章學習更多高級用法。
边栏推荐
- The report of the state of world food security and nutrition was released: the number of hungry people in the world increased to 828million in 2021
- [paddleseg source code reading] add boundary IOU calculation in paddleseg validation (1) -- val.py file details tips
- Simple configuration of single arm routing and layer 3 switching
- Datasimba launched wechat applet, and datanuza accepted the test of the whole scene| StartDT Hackathon
- 强化学习-学习笔记8 | Q-learning
- Using stored procedures, timers, triggers to solve data analysis problems
- What are the financial products in 2022? What are suitable for beginners?
- 海量数据去重的hash,bitmap与布隆过滤器Bloom Filter
- Cloud security daily 220707: Cisco Expressway series and telepresence video communication server have found remote attack vulnerabilities and need to be upgraded as soon as possible
- “解密”华为机器视觉军团:华为向上,产业向前
猜你喜欢
企业展厅设计中常用的三种多媒体技术形式
上市十天就下线过万台,欧尚Z6产品实力备受点赞
Five network IO models
Kubernetes DevOps CD工具对比选型
Skills of embedded C language program debugging and macro use
Year SQL audit platform
[tpm2.0 principle and Application guide] Chapter 5, 7 and 8
6.关于jwt
Classification of regression tests
Interview vipshop internship testing post, Tiktok internship testing post [true submission]
随机推荐
二叉树的基本概念和性质
RISCV64
能同时做三个分割任务的模型,性能和效率优于MaskFormer!Meta&UIUC提出通用分割模型,性能优于任务特定模型!开源!...
清华、剑桥、UIC联合推出首个中文事实核查数据集:基于证据、涵盖医疗社会等多个领域
企业展厅设计中常用的三种多媒体技术形式
Charles+drony的APP抓包
Recommend free online SMS receiving platform in 2022 (domestic and foreign)
【C语言】字符串函数
Hash, bitmap and bloom filter for mass data De duplication
持续测试(CT)实战经验分享
Some key points in the analysis of spot Silver
The report of the state of world food security and nutrition was released: the number of hungry people in the world increased to 828million in 2021
NAT地址转换
Live broadcast software construction, canvas Text Bold
Thread factory in thread pool
Static routing configuration
sqlite sql 异常 near “with“: syntax error
Redis的发布与订阅
国内的软件测试会受到偏见吗
[software test] from the direct employment of the boss of the enterprise version, looking at the resume, there is a reason why you are not covered