【问题标题】:Spring Data Rest ignoring @JsonInclude annotationSpring Data Rest忽略@JsonInclude注解
【发布时间】:2017-01-15 11:27:47
【问题描述】:

不管有没有这个注解,我的 JPA 上都有一个属性@Entity

@Entity
public class Myentity extends ResourceSupport implements Serializable {
...
    @ManyToOne(cascade = CascadeType.ALL)
    @JoinColumn(name="idrepository")
    @JsonInclude(JsonInclude.Include.ALWAYS)
    private MyentitySource entitysource;
...
}

当我返回时没有被映射:

@RequestMapping("/myentity/{uuid}")
public ResponseEntity<Myentity> getResourceById(@PathVariable("uuid") UUID uuid) {
    Myentity result = myentityRepository.findOne(uuid);
    return ResponseEntity.ok(myentityAssembler.toResource(result));
}

myentityAssembler.toResource(result) 确实包含MyentitySource entitysource,但 JSON 输出不包含。

最奇怪的是我有另一个 spring boot hatoas 项目,我使用完全相同的实体、存储库、控制器和汇编器实现,在我的 pom 上具有完全相同的依赖项和版本,以及非常相似的配置(我是没有定义任何特殊的 jackson 映射器或任何东西,只使用默认的 rest/hateoas 配置),它确实在那里工作MyentitySource entitysource 属性,它是另一个扩展 ResourceSupport 的 JPA 实体,被序列化并包含进入 JSON 输出。

我已经玩了几个小时了,但我很迷茫。我已经验证了这种行为在两个应用程序中的整个应用程序中都发生了:在任何 @Entity 上定义的 @ManyToOne 关系被映射并出现在一个应用程序的 JSON 输出中,但不在另一个应用程序中。

如何让这些字段显示在 JSON 输出中?

【问题讨论】:

  • 当我尝试重现您的问题时,情况有所不同。我必须使用@JsonInclude(value=Include.ALWAYS) 而不是@JsonInclude(JsonInclude.Include.ALWAYS)。不要认为这是问题,但您可以尝试一下。
  • 没有区别。使用 Eclipse 调试器我可以看到有一个 org.springframework.data.rest.webmvc.config.RepositoryRestMvcConfiguration$ResourceSupportHttpMessageConverterObjectMapper 有一个 BeanSerializerFactory 有一个 SerializerFactoryConfig 有一个 org.springframework.data.rest.webmvc.json.PersistentEntityJackson2Module$AssociationOmittingSerializerModifier (这是一个 BeanSerializerModifier ),我相信修饰符搞砸了我的 JPA @ManyToOne 协会。
  • 我现在将尝试编写自己的RepositoryRestMvcConfiguration 并覆盖或修改转换器以使用ObjectMapper,其序列化程序工厂配置不包含此修饰符。

标签: spring-data-rest


【解决方案1】:

如果MyentitySource 不是导出实体,则将包含entitysource。如果它是一个 - 这里似乎是这种情况 - 那么包含它是错误的。包括关联可能会导致将整个数据库发送给客户端。此外,它是具有自己 URI 的单独资源。因此,响应中包含指向该 URI 的链接。

CascadeType.ALL 意味着Myentity 是一个聚合,因此首先不应导出MyentitySource。那会解决你的问题。如果我的假设是错误的,那么您仍然可以使用 Projections 来获取 entitysource。我可以将您推荐给 Spring 的 Oliver Gierke 的 this answerthe relevant chapter of the documentation

【讨论】:

  • 我已经尝试导出 MyentitySource (我的意思是,为它定义一个存储库),根据文档应该使映射器包含资源 url,但它没有。我也尝试过不导出它(没有 repo),它应该包括它的属性(除了 id 之外的所有属性)。我在这个项目上定义了实体。基本上有一个来自不同项目的复制粘贴,它们工作正常,就像文档所说的那样。为什么他们在我的一个项目上以一种方式工作,而在另一个项目上以另一种方式工作?我没有定义任何投影或做任何特殊的事情来改变默认行为
  • 顺便说一句,感谢您链接文档。我试图在 google 和 spring boot docs 上找到它,但找不到。至少现在我知道它应该如何工作了^^
  • 另外,如果我理解概念定义,Myentity 是 MyentitySource 的聚合。 MyentitySource 是 Myentity 的一个属性(就像一个项目的关联类别)。在任何情况下,整个数据库都不会包含在这种特殊情况下,尽管我理解危险,并且当查询导致多个 Myentity 项目时,重复相同的嵌入资源可能不是最有效的,如果他们共享它,因此当 MyentitySource 也作为仇恨资源导出时嵌入其 URI 可能是一个更好的解决方案。但这也没有发生……
  • 更正:删除 repo did 解决了问题(我的第一次测试肯定做错了)。我仍然不知道为什么没有添加链接,而是在链接实体的存储库可用时添加链接,正如文档所指定的那样,但这个解决方案对我有用。谢谢:-)
猜你喜欢
  • 1970-01-01
  • 2014-12-19
  • 2019-02-18
  • 2019-07-02
  • 1970-01-01
  • 1970-01-01
  • 2019-11-29
  • 2015-11-13
  • 2018-07-07
相关资源
最近更新 更多