开发者

Jersey does not see my MessageBodyReader

I'm trying to use jersey with my own json MessageBodyReader开发者_开发知识库/MessageBodyWriter (as I am not use @XmlRootElement... annotations on my domain classes).

@Provider
@Produces(MediaType.APPLICATION_JSON)
@Consumes(MediaType.APPLICATION_JSON)
public final class MyGsonMessageBodyHandler implements MessageBodyWriter<Object>, MessageBodyReader<Object> {
...
}

Jersey uses this class as messagebodywriter (as it stops at breakpoint in the implemented method writeTo). Hovewer it does not see this class as messagebodyreader (and even when I break up this class to the separate implementations of the messagebodyreader/messagebodywriter it still refuses to use my messagebodyreader).

The testing code looks as follows (jersey-grizzly):

final Greeting greeting = resource.path("/greeting")
            .queryParam("name", name)
            .accept(MediaType.APPLICATION_JSON)
            .type(MediaType.APPLICATION_JSON)
            .get(Greeting.class);

The error I got looks as follows:

A message body reader for Java class test.Greeting, and Java type class test.Greeting, and MIME media type application/json was not found

I'm wondering what kind of magic is required for writing own MessageBodyReader?


After a while I found a root cause of the issue. My implementation of MessageBodyReader/Writer is OK (and I it works fine with RESTlet), but IF YOU USE JerseyTest, DO NOT FORGET TO ADD YOUR MessageBodyReader/Writer to it's ClientConfig:

/**
 * Creates custom REST client config which is mandatory since we don't use any JSON providers.
 * @return Jersey Client Config with the required classes to read/write in(out)coming data.
 */
private static ClientConfig createClientConfig() {
    final ClientConfig config = new DefaultClientConfig();
    config.getClasses().add(GsonMessageBodyHandler.class);
    config.getClasses().add(GsonAwareContextResolver.class);
    return config;
}

/**
 * Public ctor
 * @throws com.sun.jersey.test.framework.spi.container.TestContainerException On error
 */
public MyRestExposureTest() throws TestContainerException {
    super(new WebAppDescriptor.Builder("my.rest.package")
            .clientConfig(createClientConfig())
            .contextPath("/")
            .build());
}

Otherwise your client code would be unable to read/write your POJOs.


This is what I'm using and it's working (currently with Jersey 1.8).

public static Client createMyClient() {
    ClientConfig cc = new DefaultClientConfig();
    cc.getClasses().add(MyProviderClass1.class);
    cc.getClasses().add(MyProviderClass2.class);
    cc.getClasses().add(MyProviderClass3.class);
    return Client.create(cc);
}


I'm not sure if it's your case, but the common mistake is incorrect implementation of isReadable method.

Did you implemented it?
Do you stop there, when debugging?
Does it return true?


After trying Alex' solution, this finally worked for me:

public IntegrationTest() throws TestContainerException {
    super(new LowLevelAppDescriptor.Builder(createResourceConfig())
                  .build());
}

private static ResourceConfig createResourceConfig() {
    ResourceConfig rc = new PackagesResourceConfig("com.github.joschi.jersey.security.smime");
    rc.getSingletons().add(new EnvelopedWriter());
    rc.getSingletons().add(new SignedWriter());
    return rc;
}
0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜