Welcome to part 2 of the discussion of the GWT Validation Library.
In the first part I mostly spoke about why GWT-VL was made and how you can easily add richly presented client side validations to your GWT app.
In the second part I will speak about how you can connect the server side validations to the client side without much effort.
One of the design goals of the GWT Validation Library was to enable the developer to create richly presented client side validation while at the same time being able to profit from this “richness” even on the server side. So as the server side discovers errorneous input these errors should be presented to the user with the same mechanisms we already used to present the client side errors. To accomplish this goal something like a communication protocol was created. That protocol is able to push validation errors, sourced from the server side, to the client side and process them in much the same way the client side validations are processed. Through this functionality the developer is able to just concentrate on the plain validation on the server side with out having to code functionality that ensures that the errors from the server side are shown nicely to the end user.
So the GWT Validation Library consists of two parts:
- The client side part that is responsible to do client side validations and show “nice” validation messages
- The server side part that is responsible for checking the input and communicating validation messages back to the client
The server side communicates its validation messages through one object: ValidationException. This object holds the validation errors that occured on the server side. The client side has the functionality for taking that object, parsing it and invoking all the Actions’s that need to be invoked, thus resulting in the validation messages being presented to the user the same way the client side errors were presented to him/her.
So from the developers point of view its like he/she just defines how the errors should be presented once and on the server side he/she doesn’t have to care about anything view related.
Lets remember the dialog shown in part 1 of this series. Here it is again:

Input dialog
We have set it up with Validators for the fields and Actions that change the border color (background color in case of select boxes) to red if a validation error occured. Till now we only have client side validations so a malicious user could send ANY data to our backend services, additionally we might have checks that can only be done on the server side.
For this case there are utility methods provided by GWT-VL that you can use to simply check the input and return an object that the client validator understands.
Assume the following code from a service method that is responsible for saving the data the user put into the dialog above to the database:
public void addGame(Game game) throws ValidationException {
new ServerValidation()
.notEquals(game.getHomePlayer(), game.getAwayPlayer(), "homePlayer, awayPlayer");
gameDao.save(game);
}
This code actually checks whether the player of the home team and the player of the away team aren’t equal. If they are not equal the call to gameDao.save(game); will happen. If they are equal the call to notEquals will throw a ValidationException. This is actually all you have to do to wire the client side “richness” of validation messages to the server side (at least on the server side, but not much more on the client side). The ServerValidation class is provided by the GWT-Validation Library and contains some basic checks. Of importance is the fact that the service method needs to declare to throw a ValidationException (could also declare to throw the more general RuntimeException).
On the client side all we have to do to let the client side code consume the validation messages and invoke the appropriate actions is the following:
GameService ga = GameServiceAsync.instance();
ga.save(game, new AsyncCallback() {
public void onFailure(Throwable caught) {
if(caught instanceof ValidationException) {
ValidationException ex = (ValidationException) caught;
validator.processServerErrors(ex); //The ValidationProcessor instance; check the first part of this series
}
}
public void onSuccess(Void value) {
//Saving successful! Close the dialog or something.
}
}
We have now connected server side validation messages with the client side presentation logic! As you see the GWT Validation Library makes it really easy to connect client and server side validations.
What if you need different methods for checking the input than the ServerValidation class provides? Easy. You just write your tests and if they fail, you can easily talk them back to the client by using another feature of the ServerValidation class:
public void saveGame(Game game) throws ValidationException {
if(playerDisabled(game.getHomePlayer())) {
//We discovered through some custom code that the home player choosen is actually disabled
//at this time, so we don't allow to save this game.
//Now we need to make sure that the error gets to the user "nicely"
ServerValidation.exception("player_disabled", "homePlayer");
}
}
So you can just invoke the ServerValidation.exception() method to communicate custom validation errors to the client. The client will, accordingly to the second parameter (”homePlayer”), invoke all the actions for the specific component. The error message will be created through the message key (”player_disabled”) given as the first parameter (just a key because it will be i18n on the client side to the locale the user is using. Check the next post for more info about i18n!).
Here you can see the possibilites the GWT-VL gives you as a developer. You can do all the checks you can think of on the server side. The GWT-VL library tries to not limit you with what you can do but enables you to still be able to profit from it (You will also see in the third part with how the library tries to NOT limit you on how exactly you want to implement i18n).
Bringing Hibernate to the game
As I mentioned in the first post I am using Hibernate in my projects. I wanted to have a way that the nicely presented validation messages could benefit from the Hibernate-Validator stuff. So I created some additional functionality to talk back Hibernate-Validator messages to the client. So I can use the Hibernate-Validator messages and present them to the user (of course fully i18n’able) with almost no effort.
We start with a simple introduction. We might have the following Hibernate-Validator annotated class:
class Car implements Serializable {
private Long id;
private int hp;
private String model;
@Id
@GeneratedValue
public Long getId() {
return id;
}
@Range(min=10,max=500)
public int getHp() {
return hp;
}
@NotEmpty
public String getModel() {
return model;
}
... //Setters ommited
}
So we have a Car that has members for its motor power and its model. Each of these members is annotated with Hibernate-Validator specific annotations, that constrain the possible values that these member variables can hold. These annotations will trigger validation of the fields values when a Car object is persisted or updated in the database layer through hibernate. For example we can not set the model to an empty string and successfully persist/update, because of the @NotEmpty annotation.
When we want to profit from these existing validations all we have to do is to edit our DAO code a little bit to hook the GWT Validation Library in the process. For example we could have a generic dao that does persisting and updating for all of the existing model classes. What we need to change are the methods responsible for writing data to the database. I usually create two methods: “persist” and “update” which look like this:
...
public void persist(T instance) {
getHibernateSession().persist(instance);
getHibernateSession().flush();
}
public void update(T instance) {
getHibernateSession().saveOrUpdate(instance);
getHibernateSession().flush();
}
...
To let the GWT Validation Library consume the validation errors thrown from Hibernate-Validator we would change these two methods to the following (we could also go for an aspect driven approach!):
...
public void persist(T instance) {
try {
getHibernateSession().persist(instance);
getHibernateSession().flush();
}catch(InvalidStateException ex) {
ExceptionConverter.createValidationException(ex);
}catch(PropertyValueException ex) {
ExceptionConverter.createValidationException(ex);
}
}
public void update(T instance) {
try {
getHibernateSession().saveOrUpdate(instance);
getHibernateSession().flush();
}catch(InvalidStateException ex) {
ExceptionConverter.createValidationException(ex);
}catch(PropertyValueException ex) {
ExceptionConverter.createValidationException(ex);
}
}
...
The ExceptionConverter is a class of the GWT Validation Library that processes the hibernate validation exceptions and creates ValidationException’s that are understood by GWT-VL. The Hibernate-Validator indicates on which member a validation failed through the name of the member. So be sure to name the properties on the client side, which you add validators to, the same as the corresponding property of the bean. So for example in the Car object we validate that the field hp is between 10 and 500. So on the client side the validations added to the input field for the ‘hp’ should be done like:
validator.addValidators("hp",
new IntegerValidator(0,500)
.addActionForFailure(new FocusAction)
);
Note that the first parameter to the addValidators method must be the same as the field name on the Car class.
The nice thing is, we now have client side and server side validation included while at the same time profiting from the rich representation of validation errors also on errors that come directly from hibernate. And, as its one of the main goals for the GWT-VL, we can i18n all the errors, that means even the Hibernate-Validator messages.
So that was it for today in the next part I will blog about the possibilities you have to i18n all of the validation messages that are built in and the custom ones that you probably will add.
Also the Showcase site was updated, there is a description functionality that informs the user about how correct input should look like for a specific field.
You can download the GWT Validation Library at https://sourceforge.net/projects/gwt-vl/
and see the official documentation on http://gwt-vl.sourceforge.net/