Bean Validation runtime throws ConstraintViolationException on validation failure. By default Jersey uses an ExceptionMapper to return 'Bad Request' (400) error as we saw in the last example. If interested, you can check out this source code to see how Jersey implemented that.
In this example (which is an enchantment of the last example), we will implement our own ExceptionMapper to return custom validation error message.
Example
Writing the ExceptionMapper
@Provider
public class MyExceptionMapper
implements ExceptionMapper<ConstraintViolationException> {
@Override
public Response toResponse(final ConstraintViolationException exception) {
return Response.status(Response.Status.BAD_REQUEST)
.entity(prepareMessage(exception))
.type("text/plain")
.build();
}
private String prepareMessage(ConstraintViolationException exception) {
String msg = "";
for (ConstraintViolation<?> cv : exception.getConstraintViolations()) {
msg+=cv.getPropertyPath()+" "+cv.getMessage()+"\n";
}
return msg;
}
}
A JAX-RS resource with constraint annotations
@Path("/customers")
public class CustomerResource {
@POST
@Consumes(MediaType.APPLICATION_FORM_URLENCODED)
public String createCustomer(@NotNull @FormParam("name") String name,
@NotNull @FormParam("address") String address,
@NotNull @Pattern(regexp = "\\d{3}-\\d{3}-\\d{4}")
@FormParam("phone-number") String phoneNumber) {
System.out.println("-- in createCustomer() method --");
return String.format("created dummy customer name: %s, address: %s, phoneNumber:%s%n"
, name, address, phoneNumber);
}
}
To try examples, run embedded tomcat (configured in pom.xml of example project below):
mvn tomcat7:run-war
JAX-RS client
public class MyClient {
public static void main(String[] args) throws Exception {
Form form = new Form();
form.param("name", null)
.param("address", null)
.param("phone-number", "343-343-343");
Client client = ClientBuilder.newBuilder().build();
WebTarget target =
client.target("http://localhost:8080/customers");
Future<Response> future = target.request(MediaType.APPLICATION_FORM_URLENCODED)
.buildPost(Entity.form(form))
.submit(Response.class);
Response r = future.get();
if (r.getStatus() != Response.Status.OK.getStatusCode()) {
System.out.println(r.getStatus() + " - " + r.getStatusInfo());
}
System.out.println(r.readEntity(String.class));
}
} Output400 - Bad Request createCustomer.arg0 may not be null createCustomer.arg1 may not be null createCustomer.arg2 must match "\d{3}-\d{3}-\d{4}"
Note that, in above JAX-RS client, we captured Response.class instead of directly reading message body via String.class. This is to avoid ExecutionException which wraps WebApplicationException or one of its subclasses (if the response status code is not successful). See the Invocation.submit() for details.
Example ProjectDependencies and Technologies Used: - jersey-server 2.25.1: Jersey core server implementation.
- jersey-container-servlet 2.25.1: Jersey core Servlet 3.x implementation.
- jersey-bean-validation 2.25.1:
Jersey extension module providing support for Bean Validation (JSR-349) API.
- JDK 1.8
- Maven 3.5.4
|