24

I have a Java backend with Spring MVC and I am using validation in this way on my domain object for an email address:

import javax.validation.constraints.NotNull;
import javax.validation.constraints.Pattern;
import javax.validation.constraints.Size;
...
@NotNull
@Size(min = 1, max = 100)
@Pattern(regexp="^([a-zA-Z0-9\\-\\.\\_]+)'+'(\\@)([a-zA-Z0-9\\-\\.]+)'+'(\\.)([a-zA-Z]{2,4})$")
private String email;

But all I get with these lines of code

Set<ConstraintViolation<Person>> failures = validator.validate(personObject);
...
Map<String, String> failureMessages = new HashMap<String, String>();
for (ConstraintViolation<Person> failure : failures) {
    failureMessages.put(failure.getPropertyPath().toString(), failure.getMessage());
    System.out.println(failure.getPropertyPath().toString()+" - "+failure.getMessage())
}

I get this on the console:

email - must match "^([a-zA-Z0-9\\-\\.\\_]+)'+'(\\@)([a-zA-Z0-9\\-\\.]+)'+'(\\.)([a-zA-Z]{2,4})$"

but I have as email address test@test.com, so the regexp does not match.

So I have two prolems:

  • What's wrong here?
  • And how can I define a error message on my own, because display this to the user, that is not a good thing :-)

Thank you in advance for your help and Best Regards.

Tim
  • 13,228
  • 36
  • 108
  • 159

4 Answers4

46

If you use Hibernate Validator you can use @Email annotation Anyway you can create your custom contraint annotation and set a custom message to show in your resource properties file.

Javi
  • 19,387
  • 30
  • 102
  • 135
  • 1
    +1 I'd highly recommend using a pre-built @Email annotation. No point in doing this on your own. – GaryF Jan 14 '11 at 16:17
  • 3
    I added `@Email` annotation believing it would manage all automatically. I'm wrong. What's the sense of using this annotation if I have to add anyway a `@Pattern`? – vault Aug 07 '14 at 10:16
  • Add to your class path the hibernate-validator.jar (if using Maven check Bassem's answer). It will automatically intercept any field or property annotated with the @Email annotation. – Mike Argyriou Apr 11 '16 at 18:44
  • 1
    The @Email annotation tells me that "john@test" is a valid email address. This answer explains why: http://stackoverflow.com/questions/4459474/hibernate-validator-email-accepts-askstackoverflow-as-valid – Jean-François Beauchef Jun 21 '16 at 18:59
  • 5
    @Email also accepts [`null` and empty string as valid](https://github.com/hibernate/hibernate-validator/blob/master/engine/src/main/java/org/hibernate/validator/internal/constraintvalidators/AbstractEmailValidator.java#L51). So, you may also want to add @NotNull and @NotEmpty. – Mehmet Ataş Feb 26 '18 at 12:11
9

First try simpler regex such as this:

"\\b[A-Z0-9._%+-]+@[A-Z0-9.-]+\\.[A-Z]{2,4}\\b"

Than you can try RFC 2822 version:

"(?:[a-z0-9!#$%&'*+/=?^_`{|}~-]+(?:\\.[a-z0-9!#$%&'*+/=?^_`{|}~-]+)*|\"(?:[\\x01-\\x08\\x0b\\x0c\\x0e-\\x1f\\x21\\x23-\\x5b\\x5d-\\x7f]|\\\\[\\x01-\\x09\\x0b\\x0c\\x0e-\\x7f])*\")@(?:(?:[a-z0-9](?:[a-z0-9-]*[a-z0-9])?\\.)+[a-z0-9](?:[a-z0-9-]*[a-z0-9])?|\\[(?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.){3}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?|[a-z0-9-]*[a-z0-9]:(?:[\\x01-\\x08\\x0b\\x0c\\x0e-\\x1f\\x21-\\x5a\\x53-\\x7f]|\\\\[\\x01-\\x09\\x0b\\x0c\\x0e-\\x7f])+)\\])"

Let me know if the either worked for you.

Also take look at this package

org.springmodules.validation.bean.conf.loader.annotation.handler

here
http://www.springbyexample.org/examples/spring-modules-validation-module.html

It might be better alternative.

MatBanik
  • 26,356
  • 39
  • 116
  • 178
  • The second works, but I get another error... I have to look what is the problem `javax.validation.ConstraintViolationException: validation failed for classes [com.mydomain.myproject.domain.Person] during update time for groups [javax.validation.groups.Default, ]` – Tim Jan 12 '11 at 22:54
  • But no response. I created a question here: http://stackoverflow.com/questions/4675204/javax-validation-constraintviolationexception-validation-failed-for-classes-duri because I do not why this error occurs. If I check the object, no failures, but on committing the object to update, the error occurs. – Tim Jan 12 '11 at 23:40
  • I updated it the new question. The new problem only occurs if I put the `@Pattern` into my Person domain object. – Tim Jan 12 '11 at 23:47
8

You can use @Email from Hibernate Validator:

    <dependency>
        <groupId>org.hibernate</groupId>
        <artifactId>hibernate-validator</artifactId>
        <version>5.4.1.Final</version>
    </dependency>
naXa stands with Ukraine
  • 35,493
  • 19
  • 190
  • 259
Bassem Reda Zohdy
  • 12,662
  • 3
  • 33
  • 39
  • `@Email` has issues. Check out this question. https://stackoverflow.com/questions/50535214/javax-validation-constraints-email-matching-invalid-email-address – The Coder Jul 05 '18 at 02:49
2

Your regex has a couple of instances of '+' in it, which is kind of odd. e-mail addresses aren't usually required to have single quotes in them :) I think perhaps that is meant to be concatenating pieces of the String, and those should be double quotes?

For defining your own message, you just add message="{someWay.of.definingCodes}" to the annotation. Then define a translation for it in ValidationMessages.properties in the default package.

Alternately hibernate validator provides org.hibernate.validator.Email if you're willing to depend on a vendor extension.

Affe
  • 47,174
  • 11
  • 83
  • 83
  • I added the message, and I created a `ValidationMessages.properties` file in my WEB-INF/messages folder with the content: `someWay.of.definingCodes=test`. But the result is `{someWay.of.definingCodes}` instead of `test`... – Tim Jan 12 '11 at 23:39
  • the default package is generally located at WEB-INF\classes :) – Affe Jan 12 '11 at 23:44
  • Oh, okay, in my Eclipse IDE the WEB-INF\classes directory seems to be empty, because I can not open it. Should I create a new file named `ValidationMessages.properties` into it? – Tim Jan 12 '11 at 23:48
  • 1
    Usually you'd leave it in the sources and let the build process move it there. If you're using Maven you'd put it in the resources directory. Otherwise just at the root of your sources. – Affe Jan 12 '11 at 23:59
  • I use Maven, I put it into the resources folder, and it works, thank you! – Tim Jan 13 '11 at 00:30