Vaadin Validator Example
Validating user input is very common, you must capture the data and validate it in some form, using a predefined set of rules that have meaning in the context that you are using the data. In this example we are going to see how to validate this data using Vaadin.
1. The tools
- Java JDK 8
- Latest Eclipse Mars
- Vaadin 7.6.5
- Tomcat Server 8
2. Introduction
Vaadin provides useful out of the box validation facilities. In this example we are going to see the most common Vaadin validators. These validators are commonly attached to a widget and its validation could be immediate or called explicit when is needed. In this example we are going to create some widgets, then we are going to attach a validator to these widgets and see how it works.
3. Prerequisites
- JDK installed
- Eclipse Mars installed and working
- Vaadin 7.6.5 plug-in installed
- Tomcat 8 installed and running
4. Set up the project
In the file menu choose File -> New -> Other
Now from the list choose Vaadin 7 project
Press next and name your project then press finish.
5. Coding the example
PropertysetItem
PropertysetItem fieldProperties = new PropertysetItem(); fieldProperties.addItemProperty("propertyStringValidator", new ObjectProperty("")); fieldProperties.addItemProperty("propertyIntegerValidator", new ObjectProperty(0)); fieldProperties.addItemProperty("propertyDoubleValidator", new ObjectProperty(0.0)); fieldProperties.addItemProperty("propertyEmailValidator", new ObjectProperty("")); fieldProperties.addItemProperty("propertyRegexpValidator", new ObjectProperty("")); fieldProperties.addItemProperty("propertyCustomValidator", new ObjectProperty(""));
We create a PropertysetItem
for each one of our widgets going to be validated. The Class for handling a set of identified Properties
is a Class for handling a set of identified Properties.
5.1 StringLengthValidator
The StringLengthValidator
, validates the length of a string. The string must has the number of characters defined, otherwise the validator raises an exception.
fieldStringValidator
TextField fieldStringValidator = new TextField(); fieldStringValidator.setNullSettingAllowed(true); fieldStringValidator.setNullRepresentation(""); fieldStringValidator.addValidator(new StringLengthValidator("The name must have 2-5 characters lenght", 2, 5, true)); fieldStringValidator.setValidationVisible(false);
We defined a TextField
and allow null values on it with fieldStringValidator.setNullSettingAllowed(true)
, also we defined the representation of null on the text field with fieldStringValidator.setNullRepresentation("")
to an empty string. Then we add the StringLengthValidator
with fieldStringValidator.addValidator
in the field, to validate the length of the string.
This method has 3 parameters. The first parameter is the error message, the second parameter is the minimum number of characters permitted to the string and the third parameter is the maximum number of characters allowed in the string. If the string breaks any of these rules then the validator raises an exception. At last we hide the validation with fieldStringValidator.setValidationVisible
.
buttonStringValidator
Button buttonStringValidator = new Button("Validate String"); buttonStringValidator.addClickListener(new Button.ClickListener() { public void buttonClick(ClickEvent event) { try { fieldStringValidator.setValidationVisible(false); fieldStringValidator.validate(); } catch (InvalidValueException e) { Notification.show("StringValidator: The name must have 2-5 characters lenght"); fieldStringValidator.setValidationVisible(true); } } });
We create a button to explicit validate the field. First when the button is clicked, we make the validation visible with fieldStringValidator.setValidationVisible(false),
then we send feedback to the user, next we call fieldStringValidator.validate()
to instruct the validator the validation of the field. If the validator finds any broken rule, then it raises an exception. In this case we show a notification indicating the the content of the field is not following the rules defined.
layoutStringValidator
HorizontalLayout layoutStringValidator = new HorizontalLayout(); layoutStringValidator.setCaption("StringValidator"); layoutStringValidator.addComponent(fieldStringValidator); layoutStringValidator.addComponent(buttonStringValidator);
We created a horizontal layout to show the text widget and the button of the string length validator.
5.2 IntegerRangeValidator
IntegerRangeValidator
checks a value inside a range. If the value is between the range, the border values inclusive everything is OK, otherwise the validator raises an InvalidValueException
. Inside the catch
block of the exception we handle the procedure to notify or correct the mistake.
fieldIntegerValidator
TextField fieldIntegerValidator = new TextField(); fieldIntegerValidator.setNullRepresentation("0"); fieldIntegerValidator.addValidator(new IntegerRangeValidator("Value must be a integer between 6 and 12", 6, 12)); fieldIntegerValidator.setValidationVisible(false);
We declare a TextField
to hold the integer. Text fields only contain strings but we can force the value to be an integer using the PropertySetItem
as we will see later. We create the text field with TextField fieldIntegerValidator = new TextField()
.
fieldIntegerValidator.setNullRepresentation("0").
We make the null representation of the field to be “0”. fieldIntegerValidator.addValidator
adds the validator to the field. IntegerRangeValidator(String, int, int)
creates the integer range validator.
This constructor has three parameters, a string that is the error message, a min value that is the left limit of the range and a max value that is the right limit of the range. fieldIntegerValidator.setValidationVisible(false)
, hides the validation feedback to the user for this example purpose.
buttonIntegerValidator
Button buttonIntegerValidator = new Button("Validate Integer Range"); buttonIntegerValidator.addClickListener(new Button.ClickListener() { public void buttonClick(ClickEvent event) { try { fieldIntegerValidator.setValidationVisible(false); fieldIntegerValidator.validate(); } catch (InvalidValueException e) { Notification.show("IntegerRangeValidator: Value must be a integer between 6 and 12"); fieldIntegerValidator.setValidationVisible(true); } } });
As before, we create a button to explicits validate the field and checks the value against the range. For example if we have min value equals to 6 and max value equals to 12, and the value introduced inside the field is 6, then everything it’s OK. If the value is less than 6 or greater than 12, then an InvalidValueException
is raised and in this case we proceed to handle the situation.
layoutIntegerValidator
HorizontalLayout layoutIntegerValidator = new HorizontalLayout(); layoutIntegerValidator.setCaption("IntegerRangeValidator"); layoutIntegerValidator.addComponent(fieldIntegerValidator); layoutIntegerValidator.addComponent(buttonIntegerValidator);
A horizontal layout is created to hold the text field and the button side to side inside the user interface. Note that you can have a caption in the layout, that is like a sub-title inside the layout.
5.3 DoubleRangeValidator
The DoubleRangeValidator
is similar to the integer range validator, just as is for a different kind of numbers and also it can handle integer values. It checks for the values inside the range including also the border values.
fieldDoubleValidator
TextField fieldDoubleValidator = new TextField(); fieldDoubleValidator.setNullRepresentation("0.0"); fieldDoubleValidator.addValidator(new DoubleRangeValidator("Integer must be a number between 3.0 and 7.0", 3.0, 7.0)); fieldDoubleValidator.setValidationVisible(false);
We create a text field to hold the value with TextField fieldDoubleValidator = new TextField().
We set the null representation of this field with fieldDoubleValidator.setNullRepresentation("0.0")
. Next we add the validator using fieldDoubleValidator.addValidator
, we create the validator with the method DoubleRangeValidator(String, Double, Double)
, that accepts three parameters.
A string to hold the error message, a double for the left limit and another double for the max value or right limit. Lastly we make the validation invisible using fieldDoubleValidator.setValidationVisible(false);
.
Button buttonDoubleValidator = new Button("Validate Double Range"); buttonDoubleValidator.addClickListener(new Button.ClickListener() { public void buttonClick(ClickEvent event) { try { fieldDoubleValidator.setValidationVisible(false); fieldDoubleValidator.validate(); } catch (InvalidValueException e) { Notification.show("DoubleRangeValidator: Value must a number be between 3.0 and 7.0"); fieldDoubleValidator.setValidationVisible(true); } } });
As before we create a button to explicits validate the field and in the catch method we send feedback to the user.
layoutDoubleValidator
HorizontalLayout layoutDoubleValidator = new HorizontalLayout(); layoutDoubleValidator.setCaption("DoubleRangeValidator"); layoutDoubleValidator.addComponent(fieldDoubleValidator); layoutDoubleValidator.addComponent(buttonDoubleValidator);
We create the layout to hold the text and the button for the double range validator. This validator checks the value written into the text field and verify that the value against 3.0 ss the minimum value and 7.0 as the maximum value.
5.4 EmailValidator
The email validator checks that the value is a RFC 822 standard email addresses, otherwise it’s raising an error. RFC 822 limits the character repertoire to ASCII, so special non ASCII characters are not allowed. When you use this email validator the regular expresion "^([a-zA-Z0-9_\\.\\-+])+@(([a-zA-Z0-9-])+\\.)+([a-zA-Z0-9]{2,4})+$"
is being checked.
fieldEmailValidator
TextField fieldEmailValidator = new TextField(); fieldEmailValidator.setRequired(true); fieldEmailValidator.addValidator(new EmailValidator("This field must be a RFC 822 standard email addresses")); fieldEmailValidator.setValidationVisible(false);
We create the text field and attach the validator to it. In this case the EmailValidator
has only one string parameter which is the error message, that is showed when the validator fails. In this case we set the property fieldEmailValidator.setRequired(true)
to indicate that this field is required.
This is like the NullValidator
with a plus of the user feedback to indicate that is required. I prefer to use this property instead of the null validator in most cases but in some other cases is better to use the null validator.
The NullValidator
checks if a value is null or not, or in other words you use the null validator when the value in the field is required. As stated before in most of the cases the setRequired
is being used.
buttonEmailValidator
Button buttonEmailValidator = new Button("Validate Email"); buttonEmailValidator.addClickListener(new Button.ClickListener() { public void buttonClick(ClickEvent event) { try { fieldEmailValidator.setValidationVisible(false); fieldEmailValidator.validate(); } catch (EmptyValueException e){ Notification.show("email is required"); fieldEmailValidator.setValidationVisible(true); } catch (InvalidValueException e) { Notification.show("This field must be a RFC 822 standard email addresses"); fieldEmailValidator.setValidationVisible(true); } } });
We create the button and the respective ClickEvent
, and in this case we have two catch blocks. The EmptyValueException
catch block checks when the error is being raised because there is no value in the field and the InvalidValueException
is raised when the email validator finds a value that doesn’t fit in the rule regular expression.
layoutEmailValidator
HorizontalLayout layoutEmailValidator = new HorizontalLayout(); layoutEmailValidator.setCaption("EmailValidator"); layoutEmailValidator.addComponent(fieldEmailValidator); layoutEmailValidator.addComponent(buttonEmailValidator);
No we add the widgets to a horizontal layout as before.
5.5 RegexpValidator
The RegexpValidator
uses a regular expression to validate the field. If the content of the field accomplishes with the regular expression the validator passes, otherwise the validator raises an error.
fieldRegexpValidator
TextField fieldRegexpValidator = new TextField(); fieldRegexpValidator.addValidator(new RegexpValidator("^G", "The first letter must be G")); fieldRegexpValidator.setValidationVisible(false);
We create a TextField
with TextField fieldRegexpValidator = new TextField()
, and then we add a validator with fieldRegexpValidator.addValidator
. We create the validator with new RegexpValidator("^G", "The first letter must be G").
This validator has two parameters. The first parameter is the regular expression to be applied in the field. In this case we are using "^G"
, the regular expression used is true when the text in the text field begins with the letter “G” with the case included. Also we make the validation invisible with fieldRegexpValidator.setValidationVisible(false);
.
buttonRegexpValidator
Button buttonRegexpValidator = new Button("Validate Regexp"); buttonRegexpValidator.addClickListener(new Button.ClickListener() { public void buttonClick(ClickEvent event) { try { fieldRegexpValidator.setValidationVisible(false); fieldRegexpValidator.validate(); } catch (InvalidValueException e) { Notification.show("The first letter must be G"); fieldRegexpValidator.setValidationVisible(true); } } });
This is the button used to validate the regular expression, when you click on it, it makes the regular expression validates against the text field.
layoutRegexpValidator
HorizontalLayout layoutRegexpValidator = new HorizontalLayout(); layoutRegexpValidator.setCaption("RegexpValidator"); layoutRegexpValidator.addComponent(fieldRegexpValidator); layoutRegexpValidator.addComponent(buttonRegexpValidator);
Again we add the text field and the button to a horizontal layout to see it side by side.
5.6 CustomValidator
CustomValidator.java
package com.example.vaadinvalidators; import com.vaadin.data.Validator; public class CustomValidator implements Validator { private static final long serialVersionUID = 1L; @Override public void validate(Object value) throws InvalidValueException { Integer v; try{ v = (Integer.parseInt((String)value)); }catch (NumberFormatException e){ throw new InvalidValueException("Value must be an integer"); } } }
A Class that implements Validator
, to create our custom validator. We must override the public void validate(Object value)
method to implement the custom validator. In this case we check if the content of the field is an integer otherwise an error is raised. Inside a try/catch block we parse the content of the field and try to cast it to an integer value. If the value is casted everything is fine otherwise an error is raised and throws an error message. We could pass this as a parameter but in this case is hard coded inside the class.
fieldCustomValidator
TextField fieldCustomValidator = new TextField(); fieldCustomValidator.addValidator(new CustomValidator()); fieldCustomValidator.setValidationVisible(false);
We create the custom validator and attach it to the field. In this case no parameter is passed just because we defined it that way.
buttonCustomValidator
Button buttonCustomValidator = new Button("Custom Validator"); buttonCustomValidator.addClickListener(new Button.ClickListener() { public void buttonClick(ClickEvent event) { try { fieldCustomValidator.setValidationVisible(false); fieldCustomValidator.validate(); } catch (InvalidValueException e) { Notification.show(e.getMessage()); fieldCustomValidator.setValidationVisible(true); } } });
We create the button to explicit call the validation of the field, in this case we get the error message with e.getMessage()
because the error comes from inside the CustomValidator
class.
HorizontalLayout layoutCustomValidator = new HorizontalLayout(); layoutCustomValidator.setCaption("CustomValidator"); layoutCustomValidator.addComponent(fieldCustomValidator); layoutCustomValidator.addComponent(buttonCustomValidator);
Add the text field and the button to an horizontal layout.
fieldGroup
FieldGroup fieldGroup = new FieldGroup(fieldProperties); fieldGroup.bind(fieldStringValidator, "propertyStringValidator"); fieldGroup.bind(fieldIntegerValidator, "propertyIntegerValidator"); fieldGroup.bind(fieldDoubleValidator, "propertyDoubleValidator"); fieldGroup.bind(fieldEmailValidator, "propertyEmailValidator"); fieldGroup.bind(fieldEmailValidator, "propertyRegexpValidator"); fieldGroup.bind(fieldCustomValidator, "propertyCustomValidator");
Create a field group and bind the properties to it, to ensure the data types of the fields.
layout
layout.addComponent(layoutStringValidator); layout.addComponent(layoutIntegerValidator); layout.addComponent(layoutDoubleValidator); layout.addComponent(layoutEmailValidator); layout.addComponent(layoutRegexpValidator); layout.addComponent(layoutCustomValidator);
Finally we add all the horizontal layouts to the main layout that is a vertical layout.
6. The complete source code
VaadinvalidatorsUI.java
package com.example.vaadinvalidators; import javax.servlet.annotation.WebServlet; import com.vaadin.annotations.Theme; import com.vaadin.annotations.VaadinServletConfiguration; import com.vaadin.data.Validator.EmptyValueException; import com.vaadin.data.Validator.InvalidValueException; import com.vaadin.data.fieldgroup.FieldGroup; import com.vaadin.data.util.ObjectProperty; import com.vaadin.data.util.PropertysetItem; import com.vaadin.data.validator.DoubleRangeValidator; import com.vaadin.data.validator.EmailValidator; import com.vaadin.data.validator.IntegerRangeValidator; import com.vaadin.data.validator.RegexpValidator; import com.vaadin.data.validator.StringLengthValidator; import com.vaadin.server.VaadinRequest; import com.vaadin.server.VaadinServlet; import com.vaadin.ui.Button; import com.vaadin.ui.Button.ClickEvent; import com.vaadin.ui.HorizontalLayout; import com.vaadin.ui.Notification; import com.vaadin.ui.TextField; import com.vaadin.ui.UI; import com.vaadin.ui.VerticalLayout; @SuppressWarnings("serial") @Theme("vaadinvalidators") public class VaadinvalidatorsUI extends UI { @WebServlet(value = "/*", asyncSupported = true) @VaadinServletConfiguration(productionMode = false, ui = VaadinvalidatorsUI.class, widgetset = "com.example.vaadinvalidators.widgetset.VaadinvalidatorsWidgetset") public static class Servlet extends VaadinServlet { } @Override protected void init(VaadinRequest request) { final VerticalLayout layout = new VerticalLayout(); layout.setMargin(true); setContent(layout); PropertysetItem fieldProperties = new PropertysetItem(); fieldProperties.addItemProperty("propertyStringValidator", new ObjectProperty("")); fieldProperties.addItemProperty("propertyIntegerValidator", new ObjectProperty(0)); fieldProperties.addItemProperty("propertyDoubleValidator", new ObjectProperty(0.0)); fieldProperties.addItemProperty("propertyEmailValidator", new ObjectProperty("")); fieldProperties.addItemProperty("propertyRegexpValidator", new ObjectProperty("")); fieldProperties.addItemProperty("propertyCustomValidator", new ObjectProperty("")); TextField fieldStringValidator = new TextField(); fieldStringValidator.setNullSettingAllowed(true); fieldStringValidator.setNullRepresentation(""); fieldStringValidator.addValidator(new StringLengthValidator("The name must have 2-5 characters lenght", 2, 5, true)); fieldStringValidator.setValidationVisible(false); Button buttonStringValidator = new Button("Validate String"); buttonStringValidator.addClickListener(new Button.ClickListener() { public void buttonClick(ClickEvent event) { try { fieldStringValidator.setValidationVisible(false); fieldStringValidator.validate(); } catch (InvalidValueException e) { Notification.show("StringValidator: The name must have 2-5 characters lenght"); fieldStringValidator.setValidationVisible(true); } } }); HorizontalLayout layoutStringValidator = new HorizontalLayout(); layoutStringValidator.setCaption("StringValidator"); layoutStringValidator.addComponent(fieldStringValidator); layoutStringValidator.addComponent(buttonStringValidator); TextField fieldIntegerValidator = new TextField(); fieldIntegerValidator.setNullRepresentation("0"); fieldIntegerValidator.addValidator(new IntegerRangeValidator("Value must be a integer between 6 and 12", 6, 12)); fieldIntegerValidator.setValidationVisible(false); Button buttonIntegerValidator = new Button("Validate Integer Range"); buttonIntegerValidator.addClickListener(new Button.ClickListener() { public void buttonClick(ClickEvent event) { try { fieldIntegerValidator.setValidationVisible(false); fieldIntegerValidator.validate(); } catch (InvalidValueException e) { Notification.show("IntegerRangeValidator: Value must be a integer between 6 and 12"); fieldIntegerValidator.setValidationVisible(true); } } }); HorizontalLayout layoutIntegerValidator = new HorizontalLayout(); layoutIntegerValidator.setCaption("IntegerRangeValidator"); layoutIntegerValidator.addComponent(fieldIntegerValidator); layoutIntegerValidator.addComponent(buttonIntegerValidator); TextField fieldDoubleValidator = new TextField(); fieldDoubleValidator.setNullRepresentation("0.0"); fieldDoubleValidator.addValidator(new DoubleRangeValidator("Integer must be a number between 3.0 and 7.0", 3.0, 7.0)); fieldDoubleValidator.setValidationVisible(false); Button buttonDoubleValidator = new Button("Validate Double Range"); buttonDoubleValidator.addClickListener(new Button.ClickListener() { public void buttonClick(ClickEvent event) { try { fieldDoubleValidator.setValidationVisible(false); fieldDoubleValidator.validate(); } catch (InvalidValueException e) { Notification.show("DoubleRangeValidator: Value must a number be between 3.0 and 7.0"); fieldDoubleValidator.setValidationVisible(true); } } }); HorizontalLayout layoutDoubleValidator = new HorizontalLayout(); layoutDoubleValidator.setCaption("DoubleRangeValidator"); layoutDoubleValidator.addComponent(fieldDoubleValidator); layoutDoubleValidator.addComponent(buttonDoubleValidator); TextField fieldEmailValidator = new TextField(); fieldEmailValidator.setRequired(true); fieldEmailValidator.addValidator(new EmailValidator("This field must be a RFC 822 standard email addresses")); fieldEmailValidator.setValidationVisible(false); Button buttonEmailValidator = new Button("Validate Email"); buttonEmailValidator.addClickListener(new Button.ClickListener() { public void buttonClick(ClickEvent event) { try { fieldEmailValidator.setValidationVisible(false); fieldEmailValidator.validate(); } catch (EmptyValueException e){ Notification.show("email is required"); fieldEmailValidator.setValidationVisible(true); } catch (InvalidValueException e) { Notification.show("This field must be a RFC 822 standard email addresses"); fieldEmailValidator.setValidationVisible(true); } } }); HorizontalLayout layoutEmailValidator = new HorizontalLayout(); layoutEmailValidator.setCaption("EmailValidator"); layoutEmailValidator.addComponent(fieldEmailValidator); layoutEmailValidator.addComponent(buttonEmailValidator); TextField fieldRegexpValidator = new TextField(); fieldRegexpValidator.addValidator(new RegexpValidator("^G", "The first letter must be G")); fieldRegexpValidator.setValidationVisible(false); Button buttonRegexpValidator = new Button("Validate Regexp"); buttonRegexpValidator.addClickListener(new Button.ClickListener() { public void buttonClick(ClickEvent event) { try { fieldRegexpValidator.setValidationVisible(false); fieldRegexpValidator.validate(); } catch (InvalidValueException e) { Notification.show("The first letter must be G"); fieldRegexpValidator.setValidationVisible(true); } } }); HorizontalLayout layoutRegexpValidator = new HorizontalLayout(); layoutRegexpValidator.setCaption("RegexpValidator"); layoutRegexpValidator.addComponent(fieldRegexpValidator); layoutRegexpValidator.addComponent(buttonRegexpValidator); TextField fieldCustomValidator = new TextField(); fieldCustomValidator.addValidator(new CustomValidator()); fieldCustomValidator.setValidationVisible(false); Button buttonCustomValidator = new Button("Custom Validator"); buttonCustomValidator.addClickListener(new Button.ClickListener() { public void buttonClick(ClickEvent event) { try { fieldCustomValidator.setValidationVisible(false); fieldCustomValidator.validate(); } catch (InvalidValueException e) { Notification.show(e.getMessage()); fieldCustomValidator.setValidationVisible(true); } } }); HorizontalLayout layoutCustomValidator = new HorizontalLayout(); layoutCustomValidator.setCaption("CustomValidator"); layoutCustomValidator.addComponent(fieldCustomValidator); layoutCustomValidator.addComponent(buttonCustomValidator); FieldGroup fieldGroup = new FieldGroup(fieldProperties); fieldGroup.bind(fieldStringValidator, "propertyStringValidator"); fieldGroup.bind(fieldIntegerValidator, "propertyIntegerValidator"); fieldGroup.bind(fieldDoubleValidator, "propertyDoubleValidator"); fieldGroup.bind(fieldEmailValidator, "propertyEmailValidator"); fieldGroup.bind(fieldEmailValidator, "propertyRegexpValidator"); fieldGroup.bind(fieldCustomValidator, "propertyCustomValidator"); layout.addComponent(layoutStringValidator); layout.addComponent(layoutIntegerValidator); layout.addComponent(layoutDoubleValidator); layout.addComponent(layoutEmailValidator); layout.addComponent(layoutRegexpValidator); layout.addComponent(layoutCustomValidator); } }
CustomValidator.java
package com.example.vaadinvalidators; import com.vaadin.data.Validator; public class CustomValidator implements Validator { private static final long serialVersionUID = 1L; @Override public void validate(Object value) throws InvalidValueException { Integer v; try{ v = (Integer.parseInt((String)value)); }catch (NumberFormatException e){ throw new InvalidValueException("Value must be an integer"); } } }
7. Running the example
Right click on the project folder and choose Run as -> Run on server choose Tomcat 8 server and press finish.
8. Results
8.1 StringValidator
8.2 IntegerRangeValidator
8.3 DoubleRangeValidator
8.4 EmailValidator
8.5 RegexpValidator
8.6 CustomValidator
9. Download the Source Code
This was an example of: Vaadin Validators.