Java – Hal rendering cannot be obtained using spring HATEOAS and Jersey

I use spring initializr( https://start.spring.io/ )To create a starter application with only "Jersey (Jax - RS)" and "HATEOAS"

My goal is:

{
    "name": "Hello","count": 42,"_links": {
        "self": {
            "href": "http://localhost:8080/api/foo"
        }
    }
}

What I have now is:

{
    "name": "Hello","links": [
        {
            "rel": "self","href": "http://localhost:8080/api/foo"
        }
    ]
}

In addition to the class generated by initializr, I added this configuration

@Configuration
@ApplicationPath("api")
@Component
@EnableHypermediaSupport(type = HAL)
public class JerseyConfig extends ResourceConfig {
    public JerseyConfig() {
        registerEndpoints();
    }

    private void registerEndpoints() {
        register(FooResource.class);
    }
}

This resource (endpoint):

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

    @GET
    @Produces(MediaTypes.HAL_JSON_VALUE)
    public Resource<Foo> getFoo() {

        final Resource<Foo> fooTo = new Resource<>(new Foo("Hello",42));

        fooTo.add(JaxRsLinkBuilder.linkTo(FooResource.class).withRel("self"));

        return fooTo;
    }
}

And a virtual bean:

public class Foo {
    private String name;
    private int count;

    public Foo() {
    }

    public Foo(String name,int count) {
        this.name = name;
        this.count = count;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public int getCount() {
        return count;
    }

    public void setCount(int count) {
        this.count = count;
    }
}

I also tried to add

@EnableHypermediaSupport(type = HAL)

Next to @ springbootapplication in the application class

When I

GET localhost:8080/api/foo

I received a reply with the correct content type

application/hal+json;charset=UTF-8

But it is still in the wrong format ("link" attribute as array, installed "_links" attribute as object / map)

Solution

Just to add @ zerflagl's answer, to register jackson2halmodule, you should use a contextresolver, as described here In addition, at the top of this module, you need to use objectmapper to configure halhandlerinstantiator If you miss the last part, you will get an exception that Jackson cannot instantiate the serializer because there is no default constructor

@Provider
public class JacksonContextResolver implements ContextResolver<ObjectMapper> {

    private final ObjectMapper mapper = new ObjectMapper();

    public JacksonContextResolver() {
        mapper.registerModule(new Jackson2HalModule());
        mapper.setHandlerInstantiator(new HalHandlerInstantiator(
                new AnnotationRelProvider(),null,null));
    }

    @Override
    public ObjectMapper getContext(Class<?> type) {
        return mapper;
    }
}

Then simply register the context parser with Jersey resourceconfig

register(new JacksonContextResolver());
The content of this article comes from the network collection of netizens. It is used as a learning reference. The copyright belongs to the original author.
THE END
分享
二维码
< <上一篇
下一篇>>