Relatively simple probably. The Java 7 documentation for the ConstraintViolationBuilder interface specifies:
addNode
ConstraintValidatorContext.ConstraintViolationBuilder.NodeBuilderCustomizableContext addNode(String name)Deprecated. since 1.1 - replaced by addPropertyNode(String) and addBeanNode()
Adds a node to the path the ConstraintViolation will be associated to. name describes a single property. In particular, dot (.) is not allowed.
"Now" the documentation also includes the methods mentioned.
I had a requirement to validate some data using this, and the code is running on a JBoss AS 7.1.1-Final.
The "Getting Started"-Page of jBoss 7 mentions: "Java SE 7 can be used with JBoss AS 7". Now what I want to achieve is simple:
I have a Validator implements ConstraintValidator<AnnotationType, DomainClass>
, there I want to create a nice-looking ConstraintViolationException, that can be nicely handled by JSF / Primefaces to show a message and mark a field as invalid, but alas:
@Override
public boolean isValid(DomainClass instance, ConstraintValidatorContext context) {
// validation logic
if (valid) {
return true;
} else {
context.disableDefaultConstraintViolation();
context.buildConstraintViolationWithTemplate(message)
.addPropertyNode("locationName").addConstraintViolation();
return false;
}
}
And here's where it gets problematic... As mentioned in the documentation linked above: addPropertyNode()
is only available as of version 1.1 of the Bean Validation. Unfortunately JBoss AS 7 just includes BeanValidation version 1.0 (as visible in Getting Started Page).
I analyzed stacktraces of working validations, and saw, the propertyPath in ConstraintViolationImpl instances (as used by hibernate) uses multiple dots.
The documentation explicitly states: "In particular, dot (.) is not allowed.".
There's two possiblities now:
- Change the application server to Wildfly (or similar, where JSR 349 is implemented)
- Solve the problem using JSR 303 only using the
addNode()
-method.
For the purpose of this question, we rule out possibility 1 (impractical, possible required work).
How would I do this using Bean Validation 1.0?
In particular what is required in the placeholder for this to work properly with JSF Faces-Validation:
@Override
public boolean isValid(DomainClass instance, ConstraintValidatorContext context) {
// validation logic
if (valid) {
return true;
} else {
context.disableDefaultConstraintViolation();
context.buildConstraintViolationWithTemplate(message)
.addNode(/* Some awesome String */).addConstraintViolation();
return false;
}
}
Or last but not least, I am totally ... and overread a simpler approach to this :(