Hibernate @OneToMany尝试插入null

时间:2015-06-03 05:37:32

标签: java hibernate jpa orm hibernate-mapping

我有以下简单的例子。当它运行时,我看到QuoteRequest对象是使用自动生成的id生成的。接下来,我看到正在生成的Accidents对象,但是插入的quote_request_id为null,因此我收到错误:

专栏' quote_request_id'不能为空

@Entity
@Table(name = "Quotes")
public class QuoteRequest
{
    public QuoteRequest(){}

    @Id
    @Column(name = "quote_request_id")
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private long QuoteRequestId;


    @OneToMany(mappedBy = "quoteRequest", cascade = CascadeType.ALL)
    @OrderColumn(name = "accidents_id")
    private Accidents[] accidents;

    // Getters and setters
}

@Entity
@Table(name = "Accidents")
public class Accidents
{
    public Accidents()
    {
    }

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Column(name = "accidents_id")
    private long AccidentId;


    @Column(name = "amount", nullable = false)
    private Float amount;

    @ManyToOne(optional = false, cascade = CascadeType.ALL)
    @JoinColumn(name = "quote_request_id", nullable = false)
    private QuoteRequest quoteRequest;

    // Getters and setters
}

为什么不将新生成的ID插入事故栏?

2 个答案:

答案 0 :(得分:2)

首先,将@OneToMany从使用数组更改为使用List代替:

@OneToMany(mappedBy = "quoteRequest", cascade = CascadeType.ALL)
@OrderColumn(name = "accidents_id")
private List<Accidents> accidents = new ArrayList()<>;

确保设置关联的两侧:

QuoteRequest quoteRequest = ...
Accidents accidents = ...

quoteRequest.getAccidents().add(accident);
accident.setQuoteRequest(quoteRequest);

答案 1 :(得分:-1)

  

创建事故时,我没有设置quoteRequest属性。我应该做什么吗?我需要双向关系吗?

这就是原因。

首先,“我是否需要双向关系?”。嗯,你是唯一能说出来的人。但是,您已经拥有双向关系。顺便提一下,#include <stdio.h> int main(void) { int a = 5, b = 2; printf("%.2f", a/b); return 0; } 方拥有这种关系。这意味着,对于数据库列Accident依赖于字段Accident.quote_req_id。由于你没有填充该字段,Hibernate假设它是null。因此它插入null。所有预期的行为。

简而言之,您应该确保Accident.quoteRequestQuoteRequest.accident一致,例如:

Accident.quoteRequest

这只是一个非常基本的例子。简而言之,您需要class QuoteRequest { private List<Accident> accidents = new ArrayList<>(); // I prefer List or Set public void setAccidents(List<Accident> accidents) { this.accidents.clear(); if (accidents != null) { // intentionally keeping another list, to be defensive and not // affected by subsequent change in the caller's list this.accidents = this.accidents.addAll(accidents); for (Accident accident:accidents) { accident.setQuoteRequest(this); } } } } class Accident { private QuoteRequest quoteRequest; public setQuoteRequest(QuoteRequest quoteRequest) { // there will be something more... this.quoteRequest = quoteRequest; } } 设置适当的值。上面的实现中仍然存在很多问题,我将为您保留(例如,当您之前已设置Accident.quoteRequest并且现在已替换为其他列表时)