2010-04-22 79 views
2

我有兩個表:t_promo_program和t_promo_program_param。JPA級聯刪除:在NOT NULL列上將子FK設置爲​​NULL

它們由以下JPA實體表示:

@Entity 
@Table(name = "t_promo_program") 
public class PromoProgram { 
    @Id 
    @Column(name = "promo_program_id") 
    private Long id; 

    @OneToMany(cascade = {CascadeType.REMOVE}) 
    @JoinColumn(name = "promo_program_id") 
    private List<PromoProgramParam> params; 
} 

@Entity 
@Table(name = "t_promo_program_param") 
public class PromoProgramParam { 
    @Id 
    @Column(name = "promo_program_param_id") 
    private Long id; 

    //@NotNull // This is a Hibernate annotation so that my test db gets created with the NOT NULL attribute, I'm not married to this annotation. 
    @ManyToOne 
    @JoinColumn(name = "PROMO_PROGRAM_ID", referencedColumnName = "promo_program_id") 
    private PromoProgram promoProgram; 
} 

當我刪除PromoProgram,休眠打我的數據庫有:

update 
    T_PROMO_PROGRAM_PARAM 
set 
    promo_program_id=null 
where 
    promo_program_id=? 

delete 
from 
    t_promo_program 
where 
    promo_program_id=? 
    and last_change=? 

我在哪裏開始尋找丟失爲問題的根源。

回答

3

Oh crud,它是PromoProgram中缺少的「mappedBy」字段。

1

仔細檢查您是否保持雙向關聯一致性。那是;請確保鏈接到PromoProgram作爲其父項的所有PromoProgramParam實體也包含在所述父項的params列表中。如果你願意,不管哪一方「啓動」該協會,確保這種情況發生是一個好主意;如果在PromoProgramParam上調用setPromoProgram,讓setter自動將自己添加到PromoProgram的params列表中。反之亦然,當在PromoProgram上調用addPromoProgramParam時,讓它將自己設置爲參數的父項。

我以前也遇到過這個問題,這是因爲沒有保持雙向一致性。我對Hibernate進行了調試,發現它無法將刪除操作級聯到子級,因爲它們不在列表中。但是,它們肯定存在於數據庫中,並且導致FK異常,因爲Hibernate試圖刪除父項而沒有首先刪除其子項(您可能還遇到過@NonNull)。我相信製作PromoProgramParam.promoProgram字段(比如說100次)不可空的正確的「EJB 3.0」就是在@ManyToOne註釋中設置optional = false屬性。

+0

Upvoted爲「optional = false」位。 – 2010-04-22 20:49:29