Method validation and inheritance - feedback needed!
Now that everybody is returning from their summer holidays, also the Bean Validation team is getting back to their desks in order to work with full steam towards revision 1.1.
As you know, the largest new feature will be method validation, that is the validation of method parameters and return values using constraint annotations. Bean Validation 1.1 early draft 1 lays the ground for this, and right now we're tackling some advanced questions still open in that area (btw. if you haven't yet tried out the reference implementation of ED1, this is the perfect time to do so and give us your feedback).
The problem
One question the EG currently is discussing is whether and, if so, how a refinement of method constraints should be allowed in sub-types. That is, if a class implements a method of an interface or overrides a method from a super class, should the sub-type be allowed to place any additional constraints?
The current draft defines the following rules for such cases (see the draft document for all the gory details):
- No parameter constraints may be specified in addition to those constraints defined on the method in the interface or super class.
- Return value constraints may be added in sub-types.
The rationale
The rationale behind this is the principle of
behavioral sub-typing, which
demands that wherever a given type T
is used, it should be possible to replace T
with
a sub-type S
of T
. This means that a sub-type must not strengthen a method's
preconditions (by adding parameter constraints), as this might cause client code working
correctly against T
to fail when working against S
. A sub-type may also not weaken a
method's postconditions. However, a sub-type may strengthen the method's postconditions
(by adding return value constraints), as client code working against T
still will work
against S
.
Can you show me some code, please?
To give you an example, the following shows a constraint declaration considered illegal as
of the current draft, as parameter constraints are added to the placeOrder()
method in a
sub-class of OrderService
:
public class OrderService {
void placeOrder(@NotNull String customerCode, @NotNull Item item, int quantity) { ... }
}
public class SimpleOrderService extends OrderService {
@Override
public void placeOrder(
@Size(min=3, max=20) String customerCode,
Item item,
@Min(1) int quantity) { ... }
}
Alternatives
While this approach works, follows principles of clean OO design and also is employed by other Programming by Contract solutions, some voices in the EG expressed doubts whether the handling of parameter constraints isn't too restrictive and thus may limit innovation in that area. In particular with respect to legacy code, the question was raised whether it shouldn't be allowed to add parameter constraints in sub-types.
One example may be a legacy interface, which technically has no constraints (that is, no parameter constraints are placed on its methods), but comes with a verbal description of preconditions in its documentation. In this case an implementor of that interface might wish to implement this contract by placing corresponding constraint annotations on the implementation.
An open question in this situation is what should the behavior be if the interface is being constrained afterwards?
Give use your feedback!
So what do you think, should such a refinement of parameter constraints be allowed or not? Possible alternatives:
- allow such a refinement by default
- have some sort of switch controlling the behavior (either standardized or provider-specific)
As there are pro's and con's of either approach, we'd very interested in user feedback on this.
Let us know what you think by posting a comment directly to this blog, shooting a message to the mailing list or participating in this Doodle vote. Which use cases you have encountered come to mind where the possibility to refine parameter constraints may help you?
Hibernate Validator 5 alpha for Bean Validation 1.1 is out
Hibernate Validator, the reference implementation for Bean Validation has just been released in version 5 alpha. This version implements the new features described in Bean Validation 1.1 first draft.
Integrators, spec leads and users should all go and try this release to see if some adjustments are needed. On the menu: method validation, dependency injection and more.
Read more about it in Hardy's blog post.
Continuous publication of the specification snapshot
The latest snapshot of the specification is now always published on the site as soon as we push change to the Git repository. The expert group has been using it for a while, we simply forgot to announce it publicly.
Bean Validation 1.1 officially reaches the JCP
Bean Validation 1.1 early draft 1 officially reaches the JCP and is available on their website. You already knew about it from the release and artifacts announcements.
That's still a significant milestone that has to be reached by the JCP rules. A specification needs to produce a certain amount of output which is regulated by the JCP itself. If you are curious, I encourage you to read the process document.
Note that JSR-349 (Bean Validation 1.1) does run under the previous version of this process but in practice we obey the rules of the current version (especially in openness).
Code artifacts published for Bean Validation 1.1 early draft 1
Following the release of the first early draft for Bean Validation 1.1, we have published the code artifacts:
- the code source
- the jar
- the JavaDoc
All are available on JBoss's Maven repository. Alternatively, you can reference them in your Maven POM
<dependency>
<groupId>javax.validation</groupId>
<artifactId>validation-api</artifactId>
<version>1.1.0.Alpha1</version>
</dependency>
Enjoy.
Latest news
Stay up to date, subscribe to the news feed.