2016-07-19 3 views
4

스프링 데이터 REST 2.5.1, Jackson 2.8.0, 스프링 부트 1.3.6을 사용하고 있습니다.스프링 데이터 REST - 엔티티 목록, Java HATEOAS 클라이언트 사용

RestTemplate을 통해 리포지토리에서 간단한 엔티티 목록을 가져 오려고합니다. 나는 브라우저에서 끝점에 도달 할 수 있고 예상되는 HAL 데이터를 얻을 수 있습니다. 단일 엔티티를 검색하는 것은 다음과 같이 잘 동작합니다. 이들은 모두 기본 SDR 엔드 포인트 (예 : localhost : {port}/myEntity)를 사용합니다.

ResponseEntity<Resource<MyEntity>> responseEntity = 
    new RestTemplate() 
     .exchange(
     uri + "/1", 
      HttpMethod.GET, 
      HttpEntity.EMPTY, 
     new ParameterizedTypeReference<Resource<MyEntity>>() {}, port 
     ) 

또는 새로운 RestTemplate(). getForEntity (URI + "/ 1", MyEntity.class, 포트)의 많은으로

는 SO 질문 목록을 가져 오는 중입니다의 예를 찾아, 표시하는 것 문제. 나는 ParameterizedTypeReferenceResources, Resource, MyEntity, 배열 List로 시도했다. 모두 운이 없다.

 ResponseEntity<Resources<Resource<MyEntity>>> responseEntity = 
      new RestTemplate() 
        .exchange(
        uri, 
        HttpMethod.GET, 
        HttpEntity.EMPTY, 
        new ParameterizedTypeReference<Resources<Resource<MyEntity>>>() {} 
      , port 
      ) 

ResourcesResource는, List<MyEntity>는, MyEntity는 등의 ResponseEntity가 비어의 거의 모든 다양한 위와 같이 호출합니다. Like :

<200 OK,Resources { content: [], links: [] },{Server=[Apache-Coyote/1.1], Content-Type=[application/json;charset=UTF-8], Transfer-Encoding=[chunked], Date=[...]}> 

문자열 JSON은 브라우저에서 다음과 같이 표시됩니다.

{ 
"_embedded" : { 
"myEntities" : [ ... ] 
}, 
"_links" : { 
"self" : { 
    "href" : "http://localhost:8080/myEntity" 
}, 
"profile" : { 
    "href" : "http://localhost:8080/profile/myEntity" 
}, 
"search" : { 
    "href" : "http://localhost:8080/myEntity/search" 
} 
}, 
"page" : { 
    "size" : 20, 
    "totalElements" : 10, 
    "totalPages" : 1, 
    "number" : 1 
} 
} 

저장소 정의 : 내가 놓친 거지 무엇에

@RepositoryRestResource(collectionResourceRel = "myEntities", path = "myEntity") 
public interface MyEntityRepository extends PagingAndSortingRepository<MyEntity, Long> 
, QueryDslPredicateExecutor<MyEntity> 
, QuerydslBinderCustomizer<QMyEntity> { } 

어떤 생각?

+0

'Resources'의 구조를 보면 JSON 문서의 구조와 다른 점을 알 수 있습니다. 마치 자동차 열쇠로 집을 열려고하는 것과 같습니다. – zeroflagL

+0

그래, 나는 노력하고있는 방식이 효과가 없다는 것을 알았다. 나는 무엇이 효과가 있는지 알아 내려고 노력하고 있습니다. SDR에서이 형식을 생성하는 경우 SDR에서이 형식을 사용하려고 할 때 Spring 클래스가 있어야합니다. 나는 표준 형식으로 내 자신을 굴릴 필요가 없어야한다. – JudgingNotJudging

+1

예제에서 문서의 기초는'PagedResources'입니다. '_embedded'는'EmbeddedWrapper'에 의존합니다. 그러나 문서를 직접 표현하는 클래스는 없습니다. '_embedded' 속성이 동적이기 때문에 문서가 동적으로 빌드됩니다. – zeroflagL

답변

5

몇 가지 작업을 통해이 문제를 해결했습니다.

  1. 스프링 - 증오로 업데이트해야했습니다 : 0.20.0.RELEASE 0.19.0. spring-hateoas : 0.19.0은 지정된 here으로 jackson 2.7+를 지원하지 않았습니다.

  2. 다음과 같이 클라이언트를 업데이트했습니다.

    ObjectMapper mapper = builder.build() 
    MappingJackson2HttpMessageConverter messageConverter = new MappingJackson2HttpMessageConverter(); 
    
    messageConverter.setSupportedMediaTypes(MediaType.parseMediaTypes("application/hal+json")) 
    messageConverter.setObjectMapper(mapper) 
    
    ResponseEntity<PagedResources<MyEntity>> responseEntity = 
         new RestTemplate(Arrays.asList(messageConverter)) 
           .exchange(
           uri, 
           HttpMethod.GET, 
           HttpEntity.EMPTY, 
           new ParameterizedTypeReference<PagedResources<MyEntity>>() {}, port 
         ) 
    

PagedResources 이제 다음과 같습니다

<200 OK,PagedResource { content: [{<List of MyEntities>}], metadata: Metadata { number: 0, total pages: 1, total elements: 10, size: 20 }, links: [<List of hateoas links for MyEntities>] },{Server=[Apache-Coyote/1.1], Content-Type=[application/hal+json;charset=UTF-8], Transfer-Encoding=[chunked], Date=[Thu, 21 Jul 2016 14:57:18 GMT]}> 

@ zeroflagL의 코멘트 나 결국에 주도 PagedResources 구현, 좀 더 자세히보고 있어요 '아하!' 순간이 blog입니다.

해당 비트는 기본값 RestTemplate이 수락 헤더를 application/hal+json으로 설정하지 않는다는 것입니다. 대신 기본값은 application/x-spring-data-compact+json;charset=UTF-8이며 내용과 링크 만 포함하고 있습니다. 이것이 내 Resources 유형에 대해 비어있는 콘텐츠를 얻는 이유입니다. 위와 같이 MediaType을 명시 적으로 설정하면 문제가 해결됩니다.