返回json意外,将“链接”拼写为“_links”并且结构不同,在Spring hateoas中

正如标题所说,我有一个资源对象Product扩展ResourceSupport 。 但是,我收到的回复有“_links”而不是“links”属性,并且具有不同的结构。

 { "productId" : 1, "name" : "2", "_links" : { "self" : { "href" : "http://localhost:8080/products/1" } } } 

基于HATEOAS参考 ,预期是:

 { "productId" : 1, "name" : "2", "links" : [ { "rel" : "self" "href" : "http://localhost:8080/products/1" } ] } 

这是为了这个吗? 有没有办法改变它,或者如果不是结构那么就是“链接”?

我通过以下代码段添加了selfLink:

 product.add(linkTo(ProductController.class).slash(product.getProductId()).withSelfRel()); 

我使用以下构建文件的spring boot:

 dependencies { compile ("org.springframework.boot:spring-boot-starter-data-rest") { exclude module: "spring-boot-starter-tomcat" } compile "org.springframework.boot:spring-boot-starter-data-jpa" compile "org.springframework.boot:spring-boot-starter-jetty" compile "org.springframework.boot:spring-boot-starter-actuator" runtime "org.hsqldb:hsqldb:2.3.2" testCompile "junit:junit" } 

Spring Boot now(version = 1.3.3.RELEASE)有一个属性,用于控制PagedResources的输出JSON格式。

只需将以下配置添加到application.yml文件中:

 spring.hateoas.use-hal-as-default-json-media-type: false 

如果您需要输出(基于问题):

 { "productId" : 1, "name" : "2", "links" : [ { "rel" : "self" "href" : "http://localhost:8080/products/1" } ] } 

编辑:

顺便说一句,您只需要以这种方式使用@EnableSpringDataWebSupport注释。

如果您有可用的HAL,它将通过弹簧启动为您选择(并且“_links”是您使用HAL获得的)。 您应该能够手动@EnableHypermediaSupport覆盖默认值。

另一个选择是禁用整个超媒体自动配置function(这是在这里的一个spring-boot + REST示例中完成的):

 @EnableAutoConfiguration(exclude = HypermediaAutoConfiguration.class) 

据我所知,除了配置HAL之外, HypermediaAutoConfiguration并没有那么多,所以禁用它应该是完全正常的。

我注意到问题出现了,至少当你试图返回一个对象时,ResourseSupport vs 包含对象的对象扩展了ResourseSupport。 您甚至可以返回List或Array对象扩展ResourseSupport并具有相同的效果。 看例子:

 @RequestMapping(method = GET, value = "/read") public NfcCommand statusPayOrder() { return generateNfcCommand(); } 

有回应:

 { "field": "123", "_links": { "self": { "href": "http://bla_bla_bla_url" } } } 

当尝试换行为List时:

 @RequestMapping(method = GET, value = "/read") public List statusPayOrder() { return Arrays.asList(generateNfcCommand()); } 

得到:

 [ { "field": 123 "links": [ { "rel": "self", "href": "http://bla_bla_bla_url" } ] } ] 

改变答案的结构不是正确的决定,但我们可以尝试以这种方式进一步思考。

我最近有相反的问题,期望HALforms(即_links )但总是有links ,尽管使用@EnableAutoConfiguration

我的问题的解决方案也可能有所帮助。 由于我发现的一个例子的复制和粘贴,我在RestController的@RequestMapping注释中有两个mediatypes

 @RequestMapping(path="/example", produces = {MediaType.APPLICATION_JSON_VALUE, "application/hal+json"}) 

使用@EnableAutoConfiguration Spring HATEOAS仅为application/hal+json注册一个ObjectMapper,在我的应用程序中还有另一个负责MediaType.APPLICATION_JSON_VALUE ,它赢得了选择并呈现了标准JSON。

所以我的解决方案只设置generate produces="application/hal+json"以便选择Spring HATEOAS对象映射器。 在您的情况下,您应该尝试保留MediaType.APPLICATION_JSON_VALUE

我确信您正在使用带有@RepositoryRestResource注释的Spring数据

 @RepositoryRestResource public interface XX extends CrudRepository 

如果要删除默认HAL行为,可以添加以下注释参数

 @RepositoryRestResource(exported = false) public interface XX extends CrudRepository 

以上配置Spring Data REST仅公开父项目中资源的rest端点,而不必显式注释依赖项目中的每个存储库。

按照文档

隐藏某些存储库,查询方法或字段您可能根本不希望导出某个存储库,存储库上的查询方法或实体的字段。 示例包括在User对象或类似的敏感数据上隐藏密码等字段。 要告诉导出器不导出这些项,请使用@RestResource注释它们并设置exported = false。

例如,要跳过导出存储库:

 @RepositoryRestResource(exported = false) interface PersonRepository extends CrudRepository {}