Using Jackson as Jersey client serializer

后端 未结 6 1944
暖寄归人
暖寄归人 2021-01-30 13:23

Is it possible to use Jackson as the serializer/marshaller for JSON data instead of JAXB when using Jersey Client API?

If so how to configure it?

相关标签:
6条回答
  • 2021-01-30 13:46

    You might also want to try org.codehaus.jackson.jaxrs.JacksonJaxbJsonProvider (jackson-jaxrs 1.6.1).

    0 讨论(0)
  • 2021-01-30 13:49

    You may skip the creation of external config and register the provider directly:

    Client client = ClientBuilder.newClient().register(JacksonJsonProvider.class)
    
    0 讨论(0)
  • 2021-01-30 13:52

    I ran into similar issue, but for me none of the suggestions given here worked. What worked for me was below piece of code:

    import javax.ws.rs.client.ClientBuilder;
    import javax.ws.rs.client.Client;
    ...
    
    ClientBuilder clientBuilder = ClientBuilder.newBuilder()
    clientBuilder.register(JacksonFeature.class);
    ...
    Client client = clientBuilder.build();
    

    The key change was usage of JacksonFeature.class - it comes from jersey-media-json-jackson-x.yy.jar

    I got clue to use this solution from this article - http://www.baeldung.com/jersey-jax-rs-client

    0 讨论(0)
  • 2021-01-30 13:52

    For jersey 2.22.2 and Jackson 2.7.2 gradle dependencies are:

    dependencies {
        compile("com.fasterxml.jackson.jaxrs:jackson-jaxrs-json-provider:2.7.2")
        compile("org.glassfish.jersey.core:jersey-client:2.22.2")
    }
    

    Sample client code is:

    final String    name    = "world";
    final Client    client  = ClientBuilder.newClient().register(JacksonJaxbJsonProvider.class);
    final WebTarget target  = client.target("http://localhost:8080").path("hello").path(name);
    final Message   message = target.request().get(Message.class);
    
    System.out.println(message.getWelcomeMessage()); // hello world
    
    0 讨论(0)
  • 2021-01-30 14:09

    OK, I found it out, it turns out to be quite simple after all:

    ClientConfig cc = new DefaultClientConfig();
    cc.getClasses().add(JacksonJsonProvider.class);
    Client clientWithJacksonSerializer = Client.create(cc);
    

    The JacksonJsonProvider comes from the jackson-jaxrs package.

    0 讨论(0)
  • 2021-01-30 14:11

    Solution with JacksonJaxbJsonProvider

    Common way how to use Jackson with custom configuration in Jersey client was to use JacksonJaxbJsonProvider for example like this

    JacksonJaxbJsonProvider provider = new JacksonJaxbJsonProvider();
    provider.setMapper(yourObjectMapper());
    Client client = ClientBuilder.newClient(new ClientConfig(provider));
    

    Unfortunately in Jersey 2.26 they copied JacksonJaxbJsonProvider class from com.fasterxml.jackson.jaxrs:jackson-jaxrs-json-provider artifact (Jackson) to org.glassfish.jersey.media:jersey-media-json-jackson artifact (Jersey) and changed package from com.fasterxml.jackson.jaxrs.json to org.glassfish.jersey.jackson.internal.jackson.jaxrs.json.

    It is still possible to use this approach it's just needed to change JacksonJaxbJsonProvider import.

    Apart from JacksonJaxbJsonProvider being now in internal package drawback is also that you must know on which Jersey version your code runs which might be a problem when different dependencies require different Jersey versions.

    Better solution with ContextResolver<ObjectMapper>

    Better possibility how to configure Jackson in Jersey client is to use the same way how it is configured in Jersey server which is to create ObjectMapper provider like this:

    @Provider
    @Produces(MediaType.APPLICATION_JSON)
    public class ObjectMapperProvider implements ContextResolver<ObjectMapper> {
    
        private ObjectMapper objectMapper = yourObjectMapper();
    
        @Override
        public ObjectMapper getContext(Class<?> objectType) {
            return objectMapper;
        }
    
    }
    

    and use it for example like this:

    ClientConfig clientConfig = new ClientConfig();
    clientConfig.register(JacksonFeature.class);  // usually auto-discovered
    clientConfig.register(new ObjectMapperProvider());
    Client client = ClientBuilder.newClient(clientConfig);
    

    If you have both the server and the client you can reuse ObjectMapperProvider class.

    It seems that this approach works from Jersey version 2.9.

    0 讨论(0)
提交回复
热议问题