|
|
package com.utils;
|
|
|
|
|
|
import java.util.Set;
|
|
|
|
|
|
import javax.validation.ConstraintViolation;
|
|
|
import javax.validation.Validation;
|
|
|
import javax.validation.Validator;
|
|
|
|
|
|
import com.entity.EIException;
|
|
|
|
|
|
/**
|
|
|
* Hibernate Validator校验工具类
|
|
|
*
|
|
|
* 核心职责:提供统一的数据验证机制,确保输入数据的合法性
|
|
|
*
|
|
|
* 技术特性:
|
|
|
* 1. 基于JSR-303/JSR-380标准(Bean Validation)
|
|
|
* 2. 使用Hibernate Validator作为实现
|
|
|
* 3. 支持分组验证
|
|
|
* 4. 统一的异常处理机制
|
|
|
*
|
|
|
* 功能特性:
|
|
|
* - 对象属性验证
|
|
|
* - 验证分组支持
|
|
|
* - 自定义错误消息
|
|
|
* - 快速失败模式
|
|
|
*
|
|
|
* 使用场景:
|
|
|
* - 控制器参数验证
|
|
|
* - 业务对象数据校验
|
|
|
* - 表单数据验证
|
|
|
* - API接口参数校验
|
|
|
*/
|
|
|
public class ValidatorUtils {
|
|
|
|
|
|
/**
|
|
|
* 验证器实例
|
|
|
* 使用静态初始化,避免重复创建
|
|
|
*/
|
|
|
private static Validator validator;
|
|
|
|
|
|
// 静态初始化块,在类加载时初始化验证器
|
|
|
static {
|
|
|
// 创建默认的验证器工厂并获取验证器实例
|
|
|
validator = Validation.buildDefaultValidatorFactory().getValidator();
|
|
|
}
|
|
|
|
|
|
/**
|
|
|
* 校验对象
|
|
|
* 对目标对象进行数据验证,如果验证失败则抛出异常
|
|
|
*
|
|
|
* @param object 待校验对象
|
|
|
* @param groups 待校验的组(可变参数,可空)
|
|
|
* @throws EIException 校验不通过时抛出异常,包含第一个错误信息
|
|
|
*/
|
|
|
public static void validateEntity(Object object, Class<?>... groups)
|
|
|
throws EIException {
|
|
|
// 执行验证,返回违反约束的集合
|
|
|
Set<ConstraintViolation<Object>> constraintViolations = validator.validate(object, groups);
|
|
|
|
|
|
// 如果存在验证错误
|
|
|
if (!constraintViolations.isEmpty()) {
|
|
|
// 获取第一个验证错误(快速失败模式)
|
|
|
ConstraintViolation<Object> constraint = (ConstraintViolation<Object>) constraintViolations.iterator().next();
|
|
|
// 抛出业务异常,包含错误消息
|
|
|
throw new EIException(constraint.getMessage());
|
|
|
}
|
|
|
}
|
|
|
|
|
|
// 可以添加的增强方法:
|
|
|
|
|
|
/**
|
|
|
* 校验对象并返回所有错误信息
|
|
|
*
|
|
|
* @param object 待校验对象
|
|
|
* @param groups 校验分组
|
|
|
* @return 错误信息集合,如果验证通过返回空集合
|
|
|
*/
|
|
|
public static Set<ConstraintViolation<Object>> validateEntityWithDetails(Object object, Class<?>... groups) {
|
|
|
return validator.validate(object, groups);
|
|
|
}
|
|
|
|
|
|
/**
|
|
|
* 校验对象并返回所有错误消息
|
|
|
*
|
|
|
* @param object 待校验对象
|
|
|
* @param groups 校验分组
|
|
|
* @return 错误消息列表
|
|
|
*/
|
|
|
public static Set<String> validateEntityMessages(Object object, Class<?>... groups) {
|
|
|
Set<ConstraintViolation<Object>> violations = validator.validate(object, groups);
|
|
|
Set<String> messages = new java.util.HashSet<>();
|
|
|
for (ConstraintViolation<Object> violation : violations) {
|
|
|
messages.add(violation.getMessage());
|
|
|
}
|
|
|
return messages;
|
|
|
}
|
|
|
|
|
|
/**
|
|
|
* 校验对象的特定属性
|
|
|
*
|
|
|
* @param object 待校验对象
|
|
|
* @param propertyName 属性名
|
|
|
* @param groups 校验分组
|
|
|
* @throws EIException 校验不通过时抛出异常
|
|
|
*/
|
|
|
public static void validateProperty(Object object, String propertyName, Class<?>... groups)
|
|
|
throws EIException {
|
|
|
Set<ConstraintViolation<Object>> violations = validator.validateProperty(object, propertyName, groups);
|
|
|
if (!violations.isEmpty()) {
|
|
|
ConstraintViolation<Object> constraint = violations.iterator().next();
|
|
|
throw new EIException(constraint.getMessage());
|
|
|
}
|
|
|
}
|
|
|
|
|
|
/**
|
|
|
* 校验特定属性的值
|
|
|
*
|
|
|
* @param beanType Bean类型
|
|
|
* @param propertyName 属性名
|
|
|
* @param value 属性值
|
|
|
* @param groups 校验分组
|
|
|
* @throws EIException 校验不通过时抛出异常
|
|
|
*/
|
|
|
public static void validateValue(Class<?> beanType, String propertyName, Object value, Class<?>... groups)
|
|
|
throws EIException {
|
|
|
Set<ConstraintViolation<?>> violations = validator.validateValue(beanType, propertyName, value, groups);
|
|
|
if (!violations.isEmpty()) {
|
|
|
ConstraintViolation<?> constraint = violations.iterator().next();
|
|
|
throw new EIException(constraint.getMessage());
|
|
|
}
|
|
|
}
|
|
|
|
|
|
/**
|
|
|
* 校验对象并收集所有错误信息
|
|
|
*
|
|
|
* @param object 待校验对象
|
|
|
* @param groups 校验分组
|
|
|
* @return 格式化的错误信息字符串
|
|
|
*/
|
|
|
public static String validateEntityCollectMessages(Object object, Class<?>... groups) {
|
|
|
Set<ConstraintViolation<Object>> violations = validator.validate(object, groups);
|
|
|
if (violations.isEmpty()) {
|
|
|
return null;
|
|
|
}
|
|
|
|
|
|
StringBuilder sb = new StringBuilder();
|
|
|
for (ConstraintViolation<Object> violation : violations) {
|
|
|
sb.append(violation.getPropertyPath()).append(": ").append(violation.getMessage()).append("; ");
|
|
|
}
|
|
|
return sb.toString();
|
|
|
}
|
|
|
|
|
|
/**
|
|
|
* 校验对象,如果失败抛出包含所有错误信息的异常
|
|
|
*
|
|
|
* @param object 待校验对象
|
|
|
* @param groups 校验分组
|
|
|
* @throws EIException 包含所有错误信息的异常
|
|
|
*/
|
|
|
public static void validateEntityWithAllMessages(Object object, Class<?>... groups)
|
|
|
throws EIException {
|
|
|
Set<ConstraintViolation<Object>> violations = validator.validate(object, groups);
|
|
|
if (!violations.isEmpty()) {
|
|
|
String errorMessage = validateEntityCollectMessages(object, groups);
|
|
|
throw new EIException(errorMessage);
|
|
|
}
|
|
|
}
|
|
|
|
|
|
/**
|
|
|
* 快速验证方法,用于简单的非空检查等
|
|
|
*
|
|
|
* @param object 待校验对象
|
|
|
* @throws EIException 校验失败时抛出异常
|
|
|
*/
|
|
|
public static void quickValidate(Object object) throws EIException {
|
|
|
validateEntity(object);
|
|
|
}
|
|
|
|
|
|
/**
|
|
|
* 创建分组验证的便捷方法
|
|
|
*
|
|
|
* @param object 待校验对象
|
|
|
* @param group 校验分组
|
|
|
* @throws EIException 校验失败时抛出异常
|
|
|
*/
|
|
|
public static void validateInGroup(Object object, Class<?> group) throws EIException {
|
|
|
validateEntity(object, group);
|
|
|
}
|
|
|
|
|
|
/**
|
|
|
* 验证多个对象
|
|
|
*
|
|
|
* @param objects 待校验对象数组
|
|
|
* @throws EIException 第一个校验失败的对象信息
|
|
|
*/
|
|
|
public static void validateEntities(Object... objects) throws EIException {
|
|
|
for (Object object : objects) {
|
|
|
validateEntity(object);
|
|
|
}
|
|
|
}
|
|
|
} |