2011-05-15 157 views
1

我面临着以下问题 problem冬眠唯一约束

,P:我们来看看在上面的链接

在commnets :)虽然解决它,我现在有一个关于如何的问题唯一的约束是在hibernate中实现的,我开始相信它激发了一个选择查询(我对此不确定),然后“一些如何”执行验证。

我不是很不服气,与解释

回答

4

休眠创建该列有“独特”的指标,它是那么强制执行uniquness数据库。

举例来说,如果你有一个类:

@Entity 
@Cache(usage = CacheConcurrencyStrategy.READ_WRITE) 
public class UserEmailAddressEntity { 
    @Id 
    @Basic(optional = false) 
    @GeneratedValue(strategy = GenerationType.AUTO) 
    private Long id; 

    @Basic(optional = false) 
    private boolean primaryEmail; 

    @ManyToOne(optional = false) 
    private UserEntity user; 

    @NaturalId // this means the email column must be unique 
    @Basic(optional = false) 
    private String email; 

    @Basic(optional = false) 
    private String token; 

    @Basic(optional = false) 
    private boolean verified; 
} 

休眠创建一个表像这样:(PostgreSQL的,但这个想法是一样的几乎所有RDBMS)

CREATE TABLE useremailaddressentity 
(
    id bigint NOT NULL, 
    email character varying(255) NOT NULL, 
    primaryemail boolean NOT NULL, 
    token character varying(255) NOT NULL, 
    verified boolean NOT NULL, 
    user_id bigint NOT NULL, 
    CONSTRAINT useremailaddressentity_pkey PRIMARY KEY (id), 
    CONSTRAINT fk279a5e06c843ec30 FOREIGN KEY (user_id) 
     REFERENCES userentity (id) MATCH SIMPLE 
     ON UPDATE NO ACTION ON DELETE NO ACTION, 

    -- note the `UNIQUE` here: 
    CONSTRAINT useremailaddressentity_email_key UNIQUE (email) 
) 
+0

我认为一样多,但是如果你看给定链路上的评论,你会看到,当我有得天独厚的约束..休眠被射击session.save查询(实体),当我删除约束时,它不会触发,对此有什么想法? – Sudarshan 2011-05-15 13:51:24

+0

我试图在本地重新创建该行为,但我没有任何运气,对不起:(即使有一个独特的约束,它会直接插入(对于新实体)或更新(当...更新时) – wmacura 2011-05-15 23:37:44

0

我试图复制这种行为,我使用使用grails 1.3.7,并发现它是可重复的

class Child { 
String name 
static constraints = { name(unique:true) } 

}

table created 
CREATE TABLE `child` (
    `id` BIGINT(20) NOT NULL AUTO_INCREMENT, 
    `name` VARCHAR(255) NOT NULL, 
    PRIMARY KEY (`id`), 
    UNIQUE KEY `name` (`name`) 
) 

查询上 child.save()发射

Hibernate: select this_.id as id0_0_, this_.version as version0_0_, this_.created_by as created3_0_0_, this_.date_created as date4_0_0_, this_.last_updated as last5_0_0_, this_.name as name0_0_, this_.updated_by as updated7_0_0_ from child this_ where this_.name=? 
Hibernate: insert into child (version, created_by, date_created, last_updated, name, updated_by) values (?, ?, ?, ?, ?, ?) 

究其原因,我想我休眠触发以上查询是检查唯一约束,而如果你试图执行更新那么这个查询将导致另一个在内存中具有相同标识符的对象,这可能导致非唯一性观察。

我以为这是hibernate而不是grails,没有在java/hibernate中双重检查过这个。

感谢

+0

Can任何人都可以确认这种行为是否特定于grails,在使用@UniqueConstraints时我没有看到类似的行为 – Sudarshan 2011-06-29 15:06:29

+2

这是Grails特有的,也是非常可疑的(唯一性可能会在SQL检查和tx提交之间同时发生变化) – Vincent 2013-10-01 15:53:57