REST Webservice returning 415 - Unsupported Media

2020-02-01 04:16发布

问题:

I've created a REST webservice using jax-rs and jersey that is supposed to consume JSON on a POST request. My web service class looks like this:

@Path("/webhookservice")
public class Webhook {

    @POST
    @Consumes(MediaType.APPLICATION_JSON)
    public Response readData (Song song) {

        // Prints out the song info
        System.out.println("SONG INFO \n=======================");
        System.out.println("songname: " + song.getSongname());
        System.out.println("artist: " + song.getArtist());

        // Repsonse with a HTTP 200 OK
        Response response = Response.status(200).build();
        return response;

    }

}

My Song class:

public class Song {

    private String songname;
    private String artist;

    public String getSongname () { return this.songname; }
    public String getArtist () { return this.artist; }

    public void setSongname (String songname) { this.songname = songname; }
    public void setArtist (String artist) { this.artist = artist; }

}

My web.xml (if needed)

<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xmlns="http://java.sun.com/xml/ns/javaee"
    xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd"
    id="WebApp_ID" version="3.0">

    <servlet>
        <servlet-name>SnapScan-Webhook</servlet-name>
        <servlet-class>com.sun.jersey.spi.container.servlet.ServletContainer</servlet-class>
        <init-param>
            <param-name>com.sun.jersey.config.property.packages</param-name>
            <param-value>za.co.lancet.service</param-value>
        </init-param>
        <init-param>
            <param-name>com.sun.jersey.api.json.POJOMappingFeature</param-name>
            <param-value>true</param-value>
        </init-param>
        <load-on-startup>1</load-on-startup>
    </servlet>

    <servlet-mapping>
        <servlet-name>SnapScan-Webhook</servlet-name>
        <url-pattern>/*</url-pattern>
    </servlet-mapping>

</web-app>

I'm using RESTClient a little, well, rest client... Here's a screenshot of what I'm sending:

When I send that off, I get the 415 Unsupported Media Type error. Anybody have an idea why?

回答1:

You need to send the request-header Content-Type: application/json. Seems like REST-Client does not add this header automatically for you.



回答2:

As others have pointed out, you are missing the correct header. Add Content-Type: application/json to the "Headers":



回答3:

I had the same 415 http error time ago. I simply forgot the default no-parameters constructor in my DTO classes. Adding that constructor, in a similar way as for JPA entities, solved my issue and de-serialization JSON->Object works now.

I'm not sure this is your case, looking at your code, but it could be useful to other guys falling here looking at the 415+JSON issue. Regards



回答4:

Ok so there are error codes that commonly appear during content negotiation 1) 406 - Not acceptable 2) 415 - Unsupported Media Type

406 is when the server doesn't accept the content type that is being sent under the ACCEPT header of the request.

415 is the client is sending a content-type in the request header and so server straightforwardly rejects saying unsupported media type

to overcome 406 - we must include the appropriate dependent jars say a client wants an XML input to be understood by the server, then the server needs to have XML related dependencies.

to overcome 415 - understand the media types that are supported by the server and pass the correct media type in the content-type header of the request



回答5:

It might be because you've not specified a path for the API function. You have only specified the resource path in your code.

@POST
@Path("/somepath")
@Consumes(MediaType.APPLICATION_JSON)
public Response readData (Song song) {
  ...
}


回答6:

I tend to add

@Produces({"application/json"})

to my services against the top-level Class declaration and override where appropriate.

e.g.

@Path("/foo")
@Produces({"application/json"})
public class FooRestService {


回答7:

Although it could be silly experience to share, I'm going to share it in case it saves the day of somebody else.
I had set of consecutive functions, the first was with annotation @BodyParser.Of(BodyParser.Json.class), when I commented that first function the annotation line was left uncommented by mistake, so such annotation was applied on that second function resulting in such 415 media type error
hth