RepositoryRestMvcConfiguration的ObjectMapper与Spring Boot默认的ObjectMapper?

时间:2016-12-15 18:39:28

标签: java spring-boot jackson spring-data spring-data-rest

我正在使用RepositoryRestMvcConfiguration来微调其余的存储库行为:

@Configuration
public class WebConfig extends RepositoryRestMvcConfiguration {
    @Override
    protected void configureRepositoryRestConfiguration(RepositoryRestConfiguration config) {
      config.setReturnBodyOnCreate(true);
}

缺点是扩展类带来了自己的ObjectMapper bean,导致了here所描述的混乱。建议的解决方法是使用扩展类将ObjectMapper bean标记为@Primary,但RepositoryRestMvcConfiguration中的bean在序列化嵌套实体时具有不同的行为。

让我们假设以下内容:

@Entity class Parent {
    @Id Long id;
    @OneToMany @JsonManagedReference List<Child> children;
    // usual getters and setters for fields...
}

@Entity class Child {
    @Id Long id;
    @ManyToOne @JsonBackReference Parent parent;
    @ManyToOne @JsonBackReference School school;
    public getSchooldId() { return school.getId(); }
    // usual getters and setters for fields...
}

@Entity class School {
    @Id Long id;
    @OneToMany @JsonManagedReference List<Child> children;
    // usual getters and setters for fields...
} 

使用默认的Spring Boot ObjectMapper可以得到预期的结果(渲染嵌套实体):

{"id": 1, "children":[{"id":2, "schoolId":7},{"id":3, "schooldId":8}]}

然而,来自RepositoryRestMvcConfiguration的ObjectMapper忽略了子实体:

{"id": 1}

配置RepositoryRestMvcConfiguration ObjectMapper以实现与Spring Boot默认值相同的行为的正确方法是什么?

1 个答案:

答案 0 :(得分:0)

RepositoryRestMvcConfiguration创建两个objectMapper对象。

  1. 用于内部框架的objectMapper。
  2. halObjectMapper负责渲染集合Resources和链接。
  3. 您可以尝试使用限定符自动装配objectMapper来实现所需的结果:

    @Qualifier('_halObjectMapper')
    

    编辑:用于渲染关联/嵌套属性

    Spring数据休息不会通过默认关联(reference)呈现,因为它们在HATEOAS规范(json的_link部分)下可用。 如果您想渲染关联,只需使用预测

      

    此Person有几个属性:id是主键,firstName和lastName是数据属性,address是指向另一个域对象的链接

    @Entity
    public class Person {
    
      @Id @GeneratedValue
      private Long id;
      private String firstName, lastName;
    
      @OneToOne
      private Address address;
      …
    }
    

    将呈现:

       {
      "firstName" : "Frodo",
      "lastName" : "Baggins",
      "_links" : {
        "self" : {
          "href" : "http://localhost:8080/persons/1"
        },
        "address" : {
          "href" : "http://localhost:8080/persons/1/address"
        }
        }
        }
    
      

    默认情况下,Spring Data REST将导出此域对象,包括其所有属性。 firstName和lastName将作为它们的纯数据对象导出。关于地址属性有两个选项。一种选择是为Address。

    定义一个存储库      

    还有另一条路线。如果Address域对象没有自己的存储库定义,Spring Data REST将在Person资源内部内联数据字段。