首页 > 解决方案 > 无法获取 json:无限递归

问题描述

我在尝试对发布者存储库执行 GET 时遇到无限循环。

出版商:

@Data
@AllArgsConstructor
@Entity
@Table(name = "publisher")
public class Publisher {

    @Id
    private Long publisherID;

    private String name;
    private String location;

    public Publisher(@JsonProperty("publisherID") Long publisherID,
                     @JsonProperty("name") String name,
                     @JsonProperty("location") String location) {
        this.publisherID = publisherID;
        this.name = name;
        this.location = location;
    }

    @JsonManagedReference(value="Book-Publisher")
    @OneToMany(mappedBy = "publisher", cascade = CascadeType.ALL)
    private Set<Book> books;

    public Publisher() {
    }
}

书:

@Data
@AllArgsConstructor
@Entity
@Table(name = "book")
public class Book {

    @Id

私人长ID;

private String name;

@JsonBackReference(value="Book-Publisher")
@ManyToOne
@JoinColumn(name="publisherID")
private Publisher publisher;

private int publicationYear;
private int amount;

@JsonManagedReference(value="BookAuthors-Book")
@OneToMany(mappedBy = "book", cascade = CascadeType.ALL)
private Set<BookAuthors> bookAuthors;

@JsonManagedReference(value="BookGenres-Book")
@OneToMany(mappedBy = "book", cascade = CascadeType.ALL)
private Set<BookGenres> bookGenres;

public Book(@JsonProperty("id") Long id,
            @JsonProperty("name") String name,
            @JsonProperty("publisherID") Long publisherID,
            @JsonProperty("publicationYear") int publicationYear,
            @JsonProperty("amount") int amount) {
    this.id = id;
    this.name = name;
    this.publicationYear = publicationYear;
    this.amount = amount;
    PublisherService publisherService = BeanUntil.getBean(PublisherService.class);
    this.publisher = publisherService.findByID(publisherID).get();

}
@JsonManagedReference(value="RentedBook-Book")
@OneToMany(mappedBy = "book", cascade = CascadeType.ALL)
private Set<RentedBook> rentedBooks;

public Book() {
}

}

2020-04-10 16:43:02.483 WARN 672 --- [nio-8080-exec-6] .wsmsDefaultHandlerExceptionResolver:已解决 [org.springframework.http.converter.HttpMessageNotWritableException:无法写入 JSON:无限递归(StackOverflowError);嵌套异常是 com.fasterxml.jackson.databind.JsonMappingException: Infinite recursion (StackOverflowError) (通过引用链: java.util.ArrayList[0]->com.vanyasav.domain.Publisher["books"])]

完整代码可在此处获得:

https://github.com/vanyasav/Library

标签: javajsonspring

解决方案


Publisher响应序列化列表时,Publisher将调用字段的所有 getter 方法。因此,Publisher关系字段books的 getter 也被称为 setvalue。这是递归发生的。这就是无限递归的原因。

最好不要使用实体作为响应。为发布者创建一个 DTO 类,然后将发布者实体值映射到 DTO,然后发送响应。

为了将一个模型动态映射到另一个模型,您可以使用ModleMapper


推荐阅读