将Spring HATEOAS链接转换为Object的正确方法

时间:2014-09-12 16:26:56

标签: spring hateoas spring-hateoas

我有一个非常简单的控制器发出HTTP请求并以HATEOAS格式接收一些资源。

package com.provider.spring.controller;

import java.util.List;

import org.springframework.hateoas.Link;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.client.RestTemplate;

import com.fasterxml.jackson.databind.ObjectMapper;
import com.provider.employee.EmployeeDTO;
import com.provider.http.HttpComponentsClientHttpRequestFactoryBasicAuth;
import com.provider.spring.rest.Resource;

@Controller
public class EmployeeController {

    private static final String REL_SELF = "self";
    private static final String REL_SEARCH = "search";
    private static final String REL_EMPLOYEE = "employee";
    private static final String RESOURCE_URI = "http://localhost:8080/employees";

    private RestTemplate restTemplate = new RestTemplate(new HttpComponentsClientHttpRequestFactoryBasicAuth("user", "password"));
    private List<EmployeeDTO> employees;


    @RequestMapping("/employees")
    public String getAllEmployees() {

        String result = null;
        try {
            String resultBody = restTemplate.getForObject(RESOURCE_URI, String.class);
            ObjectMapper objectMapper = new ObjectMapper();
            Resource<EmployeeDTO> resource = objectMapper.readValue(resultBody, Resource.class);

            // Get objects with relation "employee"
            for(Link l : resource.getLinks()) {
                if(l.getRel().equals(REL_EMPLOYEE)) {
                    // TODO: Construct EmployeeDTO from Link.
                    // TODO: Add EmployeeDTO to list.
                }
            }
        }
        catch(Exception e) {
            e.printStackTrace();
            result = "error";
            return result;
        }
        return result;
    }
}

是否存在将链接转换为对象的现有首选或标准方法?

有关EmployeeDTO的详细信息,请参阅此处:https://gist.github.com/Xerosigma/64469a30355f5de0228a

2 个答案:

答案 0 :(得分:5)

杰克逊有几种方法可以做到这一点:

没有自定义转化器:

ObjectMapper objectMapper = new ObjectMapper();
objectMapper.registerModule(new Jackson2HalModule());
RestTemplate restTemplate= new RestTemplate();

String resultBody = restTemplate.getForObject(link.getHref(), String.class);
EmployeeDTO resource = objectMapper.readValue(resultBody, EmployeeDTO.class);

使用自定义转换器:

ObjectMapper objectMapper = new ObjectMapper();
objectMapper.registerModule(new Jackson2HalModule());
RestTemplate restTemplate= new RestTemplate();

MappingJackson2HttpMessageConverter converter = new MappingJackson2HttpMessageConverter();
converter.setObjectMapper(objectMapper);
restTemplate.setMessageConverters(Collections.<HttpMessageConverter<?>> singletonList(converter));
EmployeeDTO resource = restTemplate.getForObject(link.getHref(), EmployeeDTO.class);

答案 1 :(得分:-1)

您可以在RestTemplate的构造函数中注册一些MessageConverters或使用setMessageConverters。两者都将HttpMessageConverters列表作为参数。 如果您将其配置为这样,则可以将exchange或getForObject-method与您期望的资源类型一起使用。 RestTemplate将遍历所有转换器并检查它是否可以将json / xml / ...转换为您的对象。

以下是一个例子:

List<HttpMessageConverter<?>> converters = new LinkedList<>();
converters.add(new MappingJacksonHttpMessageConverter());
RestTemplate template = new RestTemplate(converters);
// or use the set method
template.setMessageConverters(converters);
// make url call
Resource<EmployeeDTO> resource = template.getForObject("url", Resource.class);