简体   繁体   中英

Consume JSON string with JAX-RS

Due to RFC 7159 , a string can be a valid JSON document:

JSON-text = ws value ws
...
value = false / null / true / object / array / number / string
...
string = quotation-mark *char quotation-mark

Thus, a valid JSON can be "Hello World" .

Is it possible consume such aa JSON string with JAX-RS?

JAX-RS has a @Consumes annotation to specify the MIME media types of representations a resource can consume that were sent by the client.

Following is an example to accept a request with a application/json media type:

@Path("/foo")
public class FooResource {

    @POST
    @Consumes("application/json")
    public Response bar(InputStream entity) {
        return Response.ok.build();
    }

}

If you send a request with a header of Content-Type: application/json , a response with a 200 OK status will return to you. But if you send a request with a header of Content-Type: application/xml , a response with 406 Not Acceptable will return. It is because @Consumes specify that request with JSON is acceptable but not others.

You can observe that @Consumes is noting about how to parse a request entity, but specify what media type should be accepted.

You can see that the above example has a parameter of InputStream entity . It is in fact the request entity. You can parse in the resource method of bar with a JSON parser library, eg Jackson :

@POST
@Consumes("application/json")
public Response bar(InputStream entity) {
    ObjectMapper mapper = new ObjectMapper();
    String json = mapper.readValue(inputStream, String.class);
    System.out.println(json);
    return Response.ok.build();
}

If you send a request with a body of "Hello World", you will see "Hello World" in your console. This is because Jackson know how to parse a JSON document specified in RFC 7159, but not JAX-RS.

In fact, JAX-RS implementation like RESTEasy already have JSON support with popular JSON parser library. Therefore you can simply create a resource method as follows:

@POST
@Consumes("application/json")
public Response bar(String json) {
    System.out.println(json);
    return Response.ok.build();
}

You should get the same result.

Behind the scenes, JAX-RS has MessageBodyReader to convert HTTP request body to Java object. It is the class provide mapping services from representation to a corresponding Java type. For example, jackson-jaxrs-providers implements JAX-RS MessageBodyReader and MessageBodyWriter handlers for JSON data formats.

For more details about JAX-RS, you can have a look to JSR-000339 JAX-RS 2.0 Specification

Yes, it's possible:

@Path("foo")
public class Foo {

    @POST
    @Consumes(MediaType.APPLICATION_JSON)
    @Produces(MediaType.APPLICATION_JSON)
    public Response biz(String json) {
        return Response.ok(json).build();
    }
}

And your request would be like:

curl -X POST --header 'Content-Type: application/json' \
             --header 'Accept: application/json' \
             -d '"Hello World"' 'http://localhost:8080/api/foo'

Yes, it's possible.

On JAX-RS define your method as:

@POST
@Consumes(MediaType.APPLICATION_JSON)
public void example(String s) { ... }

On client side, send the payload without encoding to json, eg:

var payload = "helloworld"; // OK
...

Rather than:

var payload = JSON.stringify("helloworld"); // KO
...

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM