Spring Boot 多对多 GET 请求

Posted

技术标签:

【中文标题】Spring Boot 多对多 GET 请求【英文标题】:Sping boot many-to-many GET request 【发布时间】:2022-01-05 21:22:19 【问题描述】:

我的 Spring Boot 应用程序中存在多对多关系。但是当我尝试得到响应时,我总是得到一个空数组; 这是我的类(我粘贴了没有构造函数、getter 和 setter 的代码,但我的代码中有它们):

@Entity
@Table(name="orders")
public class Order 
    private @Id
    @GeneratedValue
    Long id;
    @OneToOne(cascade = CascadeType.ALL)
    private Customer customer;
    @OneToMany(mappedBy = "product",fetch = FetchType.LAZY,cascade = CascadeType.PERSIST,CascadeType.MERGE,CascadeType.DETACH,orphanRemoval = true)
    private Set<ProductOrderDetails> productOrderDetails;
    @DateTimeFormat
    private Date shippmentDate;
    private double totalOrderPrice;
    private OrderStatus status;
    private String note1;
    private String note2;

@Entity
@Table
public class Product 
    private @Id
    @GeneratedValue
    Long id;
    private String name;
    private String model;
    private String color;
    private String material;
    private double price;
    @Transient
    private int productQuantity;
    @OneToMany(mappedBy = "order",fetch = FetchType.LAZY)
    private List<ProductOrderDetails> productOrderDetailsSet;

@Entity
@IdClass(ProductOrderDetails.class)
public class ProductOrderDetails implements Serializable 

    @Id
    @ManyToOne(cascade = CascadeType.ALL)
    @JoinColumn(name="order_id")
    Order order;

    @Id
    @ManyToOne(cascade = CascadeType.PERSIST,CascadeType.MERGE,CascadeType.DETACH)
    @JoinColumn(name="product_id")
    Product product;

    private int quantity;

这是我的 OrderController 代码:

@GetMapping("/id")
    public Order One(@PathVariable Long id) 
        Order order=repository.findById(id).orElseThrow(()->new ObjectNotFoundException(id));
      return order;
    

这是我得到的回应:


    "id": 2,
    "customer": 
        "id": 1,
        "name": "Company",
        "address": "Main Street 1",
        "city": "Bern",
        "state": "Switzerland",
        "zip": 58529,
        "contactPersonName": "John Smith",
        "contactPersonEmail": "test@gmail.com"
    ,
    "productOrderDetails": [],
    "shippmentDate": "2020-12-09T23:00:00.000+00:00",
    "totalOrderPrice": 3434.0,
    "status": "WAITING",
    "note1": "note 1",
    "note2": "note 2"

如何获得 productOrderDetails 数组(订购的产品数组)? 如果我可以使用 JPA,我会更喜欢

【问题讨论】:

【参考方案1】:

你有几种可能做到这一点:

使用 FetchType.EAGER 策略
@Entity
@Table(name="orders")
public class Order 
    private @Id
    @GeneratedValue
    Long id;
    @OneToOne(cascade = CascadeType.ALL)
    private Customer customer;
    @OneToMany(mappedBy = "product",fetch = FetchType.EAGER,cascade = CascadeType.PERSIST,CascadeType.MERGE,CascadeType.DETACH,orphanRemoval = true)
    private Set<ProductOrderDetails> productOrderDetails;
    @DateTimeFormat
    private Date shippmentDate;
    private double totalOrderPrice;
    private OrderStatus status;
    private String note1;
    private String note2;

在您的自定义存储库方法中使用 Join fetching:
@Query(value = "SELECT o FROM Order o JOIN FETCH o.productOrderDetails")
List<Order> findAllOrders();

【讨论】:

对不起,如果我不清楚,但我希望在我的 JSON 响应中“productOrderDetails”不是空/空数组,我希望“productOrderDetails”包含订购产品列表GET 请求。 你有没有尝试过这些方法? 是的,我试过了:@Query("SELECT o FROM Order o left outer join fetch o.productOrderDetails pod left outer join fetch pod.product where o.id=:id") Order getOrderById(@Param("id") Long id); 但我总是让“productOrderDetails”为空。我不确定课程是否是问题【参考方案2】:

所以对于和我有同样问题的人来说, 我有一个拼写错误,在我应该使用的 Order 类中:

  @OneToMany(mappedBy = "order",fetch = FetchType.LAZY,cascade = CascadeType.PERSIST,CascadeType.MERGE,CascadeType.DETACH,orphanRemoval = true)
    private Set<ProductOrderDetails> productOrderDetails;

而不是 mappedBy="product"。 如果您不想在执行 GET 请求时进行递归调用,则应在 ProductOrderDetails 类中添加@JsonIgnore:

@Id
@ManyToOne(cascade = CascadeType.ALL)
@JoinColumn(name="order_id")
@JsonIgnore
Order order;

其余代码保持不变。

【讨论】:

以上是关于Spring Boot 多对多 GET 请求的主要内容,如果未能解决你的问题,请参考以下文章

Spring Boot JPA多对多关系-Rest Web Service无法获取Get All中的所有子属性

多对多 Spring Boot JPA 未填充多对多表

Spring-boot JPA无限循环多对多

Spring Boot 中的多对多映射问题

Spring boot - 多对多关联不删除连接表数据

Spring Boot 多对多 post 方法不更新数据