2010-11-22 53 views
3

当删除@Embeddable对象时,我遇到了一些问题。如何删除包含可空字段的Hibernate @Embeddables?

我有以下的域类:SwitchVoipTrunkGroup和PrioritizedCodec。后者包含几个可以为空的字段。

class SwitchVoipTrunkGroup { 

    //... 

    @CollectionOfElements(fetch = FetchType.LAZY) 
    @JoinTable(
      name = "SWITCH_VOIP_TKG_CODEC", 
      joinColumns = @JoinColumn(name = "FK_SWITCH_VOIP_TKG_ID") 
    ) 
    @ForeignKey(name = "FK_CODEC_SWITCH_VOIP_TKG") 
    private Set<PrioritizedCodec> prioritizedCodecs = new HashSet<PrioritizedCodec>(); 

    //... 
} 

@Embeddable 
public class PrioritizedCodec { 

    @Column(name = "PRIORITY") 
    private String priority; 

    @Column(name = "FAX_MODE") 
    private String faxMode; 

    //... some more columns ... 
} 

当我编辑SwitchVoipTrunkGroup的prioritizedCodecs字段(例如删除条目)并保存实体,我看到在我的Hibernate日志如下:

13:54:31,919 INFO [STDOUT] Hibernate: delete from T_SWITCH_VOIP_TKG_CODEC where 
fk_switch_voip_tkg_id=? and fax_mode=? and priority=? 

this question我明白为什么Hibernate使用所有where子句中的字段。然而,这会出问题:如果某些字段为空时,查询将看起来像这样:

delete from T_SWITCH_VOIP_TKG_CODEC where fk_switch_voip_tkg_id=1 and fax_mode = '' 
and priority ='' 

然而,这将不会删除任何记录,因为什么是真正必要的是让Hibernate检查NULL异为一个空字符串。例如:

delete from T_SWITCH_VOIP_TKG_CODEC where fk_switch_voip_tkg_id=1 and fax_mode 
IS NULL and priority IS NULL 

(参见here对于为什么检查空字符串不足以更多信息)

如何解决这个任何想法?很多thx!

+0

是否有一个原因,为什么你不能设置这些属性的值在执行删除操作之前在您的实体中为null? – 2010-11-22 15:05:49

+0

事实上,它们为空就是问题所在,因为这会让Hibernate检查where子句中的空字符串。 – 2010-11-23 06:57:24

+0

事情是,@Embeddable对象的概念是,他们的生命周期与他们的父母的生命周期相关联 - 删除他们而不删除他们的父母似乎关闭。 – 2010-12-03 20:26:05

回答

1

我建议规范你的数据库,所以你的类都成为实体,然后在SwitchVoipTrunkGroup和PrioritizedCodec之间建立一对多关系,然后你可以设置级联规则,这样Hibernate会自动更新PrioritizedCodec类型元素的集合,当你坚持SwitchVoipTrungGroup的实例。

或者,您可以通过@Column批注的属性指定优先级和faxMode字段默认值和强制可空约束

@Column(columnDefinition = "VARCHAR(20) default 'NONE'", nullable = false) 
private String faxMode;