java - Hibernate 多对多双向 - 双向 @JsonManagedReference 和 @JsonBackReference

标签 java json hibernate jackson

为了避免无限递归,我使用 @JsonManagedReference 和 @JsonBackReference 。但是在检索结果时,我只能以一种方式获得预期结果。

    @ManyToMany(cascade = CascadeType.ALL)
    @JoinTable(name="THIRD_TABLE", 
    joinColumns={@JoinColumn(name="STUDENT_ID")}, 
    inverseJoinColumns={@JoinColumn(name="TEACHER_ID")})
    @JsonManagedReference
    private Set<Teacher> teachers = new HashSet<>();

-----------
    @ManyToMany(mappedBy="teachers")
    @JsonBackReference
    private Set<Student> winners = new HashSet<>();

按学生计算教师数可以很好,但按教师计算学生数则行不通。 JsonBackReference 可以防止这种情况发生。

是否可以在一个字段上同时使用两个注释并使其以两种方式工作。

最佳答案

如果您只想避免递归,可以使用@JsonIdentityInfo。它会为每个对象生成id,如果重复则用id替换重复的对象。

这是一个简单的父/子示例:

@JsonIdentityInfo(generator=IntSequenceGenerator.class)
@JsonAutoDetect(fieldVisibility = Visibility.ANY, getterVisibility = Visibility.NONE, setterVisibility = Visibility.NONE)
public class Parent {
  private List<Child> children=new ArrayList<>();
  private String name="parent";

  public Parent() {
    super();
    children.add(new Child(this,"foo"));
    children.add(new Child(this,"bar"));
  }

  public List<Child> getChildren() {
    return children;
  }

}
@JsonAutoDetect(fieldVisibility = Visibility.ANY, getterVisibility = Visibility.NONE, setterVisibility = Visibility.NONE)
public class Child {
  private Parent parent;
  private String pseudo="toto";
  public Child(Parent parent, String pseudo) {
    super();
    this.parent = parent;
    this.pseudo = pseudo;
  }

}



public class SOJson {
  public static void main(String[] args) throws JsonGenerationException, JsonMappingException, IOException {
    ObjectMapper objectMapper = new ObjectMapper();
    Parent object=new Parent();
    String json1 = objectMapper.writeValueAsString( object);
    System.out.println("write parent: "+json1);
    String json2 = objectMapper.writeValueAsString(object.getChildren().get(0));
    System.out.println("write child: "+json2);

  }
}

结果:

write parent: {"@id":1,"children":[{"parent":1,"pseudo":"foo"},{"parent":1,"pseudo":"bar"}],"name":"parent"}
write child: {"parent":{"@id":1,"children":[{"parent":1,"pseudo":"foo"},{"parent":1,"pseudo":"bar"}],"name":"parent"},"pseudo":"foo"}

您会看到子级和父级之间存在递归,如果删除 @JsonIdentityInfo,您将出现堆栈溢出。

当然,您需要在某个地方停止递归,否则您将转储所有数据库!使用 @jsonIgnore 在某处停止递归,或使用 Hibernate4Module 在卸载的惰性属性上停止递归。 (我更喜欢两者都使用)

关于java - Hibernate 多对多双向 - 双向 @JsonManagedReference 和 @JsonBackReference,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/42650385/

相关文章:

java - 类路径包含多个 SLF4J 绑定(bind),排除不起作用,

java - 设置面板的背景颜色在 JTabbedPane 外部有效,但在 JTabbedPane 内部无效

json - 将 JSON 反序列化为扁平化类

AJAX 返回 JSON - 我错过了什么?

java - 在嵌入式 HSQL 数据库中创建模式的最佳方式

java - 为什么这两个子字符串调用等效?

java - Eclipse 中的 AutoIndent 可能吗?

javascript - D3js - 将数据绑定(bind)到多个圆环图

java - 如何以正确的方式处理超过锁定等待超时?

java - 将sql查询转换为hql