1

I am using Swagger to generate a Restful API:

@POST
@Consumes({ "application/json" })
@Produces({ "application/json" })
@io.swagger.annotations.ApiOperation(value = "Create a task", notes = "", response = Tasks.class)
@io.swagger.annotations.ApiResponses(value = { 
    @io.swagger.annotations.ApiResponse(code = 200, message = "created task", response = Tasks.class),
    @io.swagger.annotations.ApiResponse(code = 404, message = "task not found", response = Tasks.class),
    @io.swagger.annotations.ApiResponse(code = 200, message = "unexpected error", response = Tasks.class) })
public Response createTask(@ApiParam(value = "The task to create" ,required=true ) NewTask newTask)
throws NotFoundException {
    return delegate.createTask(newTask);
}

This API accepts json strings and generates java objects from it. This is working quiet well with one exception: The API accepts any correct formed json string but ignores the content of the json which means i get an object created with default values.

So my question is: How can i validate the incoming jsonstring ( against a json schema) before the actual java object is generated?

3
  • How do perform the validation against the schema? You can receive your JSON as String, validate it and then create a object from it using Jackson, for example. But, since you are performing validations, have you considered Bean Validation? Commented Dec 1, 2015 at 13:53
  • The problem is, i would have to change the API to receive a json string instead of an object like public Response createTask(String jsonTask) in the methods parameters afaik but i would prefer to have the object there if its possible. Commented Dec 1, 2015 at 14:17
  • You can write your own MessageBodyWriter... Commented Dec 1, 2015 at 14:24

2 Answers 2

1

Since you don't want to receive a JSON String in your methods and Bean Validation is not an option for your validation, you could try a MessageBodyWriter<T>.

JAX-RS uses MessageBodyWriter<T>s to parse incoming requests. Since you want something very specific, consider writing your own MessageBodyWriter<T>.

See the following example:

@Provider
@Produces("application/json")
public class CustomMessageBodyWriter implements MessageBodyWriter<Object> {

    @Override
    public boolean isWriteable(Class<?> type, Type genericType,
                               Annotation[] annotations, MediaType mediaType) {
        return true;
    }

    @Override
    public long getSize(MyBean myBean, Class<?> type, Type genericType,
                        Annotation[] annotations, MediaType mediaType) {

        // Deprecated by JAX-RS 2.0
        return 0;
    }

    @Override
    public void writeTo(Object object, Class<?> type, Type genericType,
                        Annotation[] annotations, MediaType mediaType,
                        MultivaluedMap<String, Object> httpHeaders,
                        OutputStream entityStream) throws IOException {

        // Read the entityStream
        // Perform the validation against your schema
        // Write to the object
    }
}

The @Provider annotation makes the class to be automatically discovered by the JAX-RS runtime during a provider scanning phase.

Sign up to request clarification or add additional context in comments.

4 Comments

One question: I am using Swagger which brings its own MessageBodyWriter. link Would i need to change the swagger source? Or is there another way i could force the use of my own implementation (without reflection)?
@Gobliins Annotating your MessageBodyWriter with @Provider or registering it to your Applicationor ResourceConfig class should be enough to it be recognized by Jersey/JAX-RS.
Err.. wouldn't i need the other way (DeSerializer)? Since the i want to verify an incoming json before mapping it to the model and not writing a model in a json stream?
@Gobliins Jersey/JAX-RS already provide a MessageBodyReader<T> for JSON. You can write your own if the provided one doesn't fit your needs.
0

There is the swagger-request-validator having several adapters for various frameworks, e.g.: Spring Web MVC

It is capable of validating requests and / or responses against Swagger / OpenAPI 2 or OpenAPI 3 schemes.

See here: Validating JSON messages against Swagger definition in Java for a more detailed answer.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.