如何使用Hibernate Validator动态解析消息参数?

我正在使用Hibernate Validator,并且想在错误消息中解析类别的名称。考虑以下简单情况:

public class Category {

private String name;

}

public class Product {

@HazardousCategoryConstraint(message = "{haz.cat.error}")

private Category category;

private String name;

}

public class InventoryReport {

@Valid

private List<Product> products;

}

ValidationMessages.properties

haz.cat.error={name} is a product in the hazardous category list.

假设我有一个HazardousCategoryConstraint的有效实现。验证器根据受限名称列表检查每个类别的名称。当我调用validate(InventoryReport)时,我得到了我期望的错误数量,但它们是相同的字符串。我希望看到类别名称解析为每条消息。有人可以给我指出一个如何动态解析参数的示例,或向我展示如何进行解析吗?

回答:

IMO,简单的解决方案是创建的自定义实现javax.validation.MessageInterpolator。将主要工作委托给Hibernate

Validator

ResourceBundleMessageInterpolator,并在中进行所需的替换工作CustomMessageInterpolator

public class CustomMessageInterpolator extends org.hibernate.validator.messageinterpolation.ResourceBundleMessageInterpolator {

private static final Pattern MESSAGE_PARAMETER_PATTERN = Pattern.compile( "(\\{[^\\}]+?\\})" );

@Override

public String interpolate(String message, Context context) {

String resolvedMessage = super.interpolate(message, context);

resolvedMessage = replacePropertyNameWithPropertyValues(resolvedMessage, context.getValidatedValue());

return resolvedMessage;

}

private String replacePropertyNameWithPropertyValues(String resolvedMessage, Object validatedValue) {

Matcher matcher = MESSAGE_PARAMETER_PATTERN.matcher( resolvedMessage );

StringBuffer sb = new StringBuffer();

while ( matcher.find() ) {

String parameter = matcher.group( 1 );

String propertyName = parameter.replace("{", "");

propertyName = propertyName.replace("}", "");

PropertyDescriptor desc = null;

try {

desc = new PropertyDescriptor(propertyName, validatedValue.getClass());

} catch (IntrospectionException ignore) {

matcher.appendReplacement( sb, parameter );

continue;

}

try {

Object propertyValue = desc.getReadMethod().invoke(validatedValue);

matcher.appendReplacement( sb, propertyValue.toString() );

} catch (Exception ignore) {

matcher.appendReplacement( sb, parameter );

}

}

matcher.appendTail( sb );

return sb.toString();

}

}

public void validate() {

Configuration<?> configuration = Validation.byDefaultProvider().configure();

ValidatorFactory validatorFactory = configuration.messageInterpolator(new CustomMessageInterpolator()).buildValidatorFactory();

Validator validator = validatorFactory.getValidator();

Product p = new Product();

Category cat = new Category();

cat.setName("s"); //assume specified name is invalid

p.setCategory(cat);

Set<ConstraintViolation<Product>> violations = validator.validate(p);

for(ConstraintViolation<Product> violation : violations) {

System.out.println(violation.getMessage());

}

}

s is a product in the hazardous category list.

以上是 如何使用Hibernate Validator动态解析消息参数? 的全部内容, 来源链接: utcz.com/qa/420755.html

回到顶部