Hibernate循环引用

时间:2017-11-12 11:55:05

标签: java hibernate

我在我的应用程序中有一对一和多对多的关系:

CREATE TABLE IF NOT EXISTS users (
  Id       INT AUTO_INCREMENT,
  Login    VARCHAR(15) UNIQUE NOT NULL,
  Password VARCHAR(20)        NOT NULL
);
CREATE TABLE IF NOT EXISTS products (
  Id    INT PRIMARY KEY AUTO_INCREMENT,
  Name  VARCHAR(30) NOT NULL,
  Price DOUBLE             NOT NULL
);
CREATE TABLE IF NOT EXISTS orders (
  Id     INT PRIMARY KEY AUTO_INCREMENT,
  UserId INT,
  FOREIGN KEY (UserId) REFERENCES users (Id)
);
CREATE TABLE IF NOT EXISTS order_products (
  Order_id   INT,
  Product_id INT,
  FOREIGN KEY (Order_id) REFERENCES orders (Id),
  FOREIGN KEY (Product_id) REFERENCES products (Id)
)

实体:

@Entity
@Table(name = "users")
public class User {

    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    @Column(name = "Id", unique = true)
    private int Id;

    @Size(min = 3, max = 15)
    @Column(name = "Login", unique = true)
    private String login;

    @NotNull
    @Size(min = 5, max = 20)
    @Column(name = "Password")
    private String password;

    @OneToMany(mappedBy = "user", fetch = FetchType.EAGER, cascade = CascadeType.ALL)
    private List<Order> orders;
}

@Entity
@Table(name = "Orders")
public class Order {

    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    @NotNull
    @Column(name = "Id", unique = true)
    private int id;

    @ManyToOne
    @JoinColumn(name = "UserId")
    private User user;

    @ManyToMany(fetch = FetchType.EAGER, cascade = CascadeType.ALL)
    @JoinTable(name = "order_products", joinColumns = {@JoinColumn(name = "Order_id")},
            inverseJoinColumns = {@JoinColumn(name = "Product_id")})
    private List<Product> products;
}

@Entity
@Table(name = "products")
public class Product {

    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    @NotNull
    @Column(name = "Id", unique = true)
    private int id;


    @NotNull
    @Size(min = 5, max = 30)
    @Column(name = "Name")
    private String name;


    @NotNull
    @Column(name = "Price")
    private double price;

    @ManyToMany(fetch = FetchType.EAGER, mappedBy = "products")
    private List<Order> orders;
}

如果我尝试访问,例如,用户,它引用订单,然后命令引用用户,最后我得到了一个java.lang.StackOverflowError。

1 个答案:

答案 0 :(得分:1)

由于实体被急切加载,这种情况正在发生。你需要懒洋洋地加载它们,这意味着它不会立即加载所有对象,而是按需加载它们。

您需要替换所有使用的地方

fetch = FetchType.EAGER

fetch = FetchType.LAZY

或仅删除fetch = FetchType.EAGER,因为fetch = FetchType.LAZY是默认加载机制。

这是一个很好的教程,可以更好地理解不同类型的加载:http://www.baeldung.com/hibernate-lazy-eager-loading