使用序列时,Hibernate会生成负的id值

时间:2012-03-25 15:38:02

标签: java hibernate jpa jboss7.x jpa-2.0

我有一个具有以下定义的类:

@Id
@SequenceGenerator(name = "SEQ_ACE_WORKERS_QUEUE_STATS_ID", sequenceName = "SEQ_ACE_WORKERS_QUEUE_STATS_ID", allocationSize = 500)
@GeneratedValue(strategy = GenerationType.SEQUENCE, generator = "SEQ_ACE_WORKERS_QUEUE_STATS_ID")
@Column(name = "ID")
private long Id;

当我们在Jboss 4.2.3上运行它时它工作正常并生成了正确的ID(从1000 +开始)

现在我们转到jboss 7.1.1并生成负ID! (从-498开始上升)

知道为什么会这样吗?

3 个答案:

答案 0 :(得分:64)

新行为如下:

AllocationSize 是为Hibernate保留的一系列主键值。 只有在hibernate使用了这一系列主键之后,才能完成双重选择seq.nextval

所以必须allocationSize(Hibernate)和序列increment by(DB)上声明相同的值

明确设置allocationSize=500时,例如在Oracle上

create sequence SEQ_ACE_WORKERS_QUEUE_STATS_ID
       MINVALUE 1 
       MAXVALUE 999999999999999999999999999 
       START WITH 1
       INCREMENT BY 500 
       NOCACHE 
       NOCYCLE;

否则,您会注意到因主键冲突而从数据库中引发的负值或约束错误。

当重新启动应用服务器时,您会注意到分配的最新主键和重启时选择的“新”序列号之间的“跳转”。

最终评论:默认值为50.因此,如果您未在Hibernate端指定allocationSize,则必须在数据库端声明increment by 50。< / p>

答案 1 :(得分:33)

从JBoss 6.1迁移到JBoss 7.1时,我遇到了这个问题。

根据JBoss AS 7.1 JPA文档(https://docs.jboss.org/author/display/AS71/JPA+Reference+Guide#JPAReferenceGuide-Persistenceunitproperties),

JBoss 7.1自动设置几个hibernate属性。正在设置的属性之一是hibernate.id.new_generator_mappings,它激活使用不同算法且不向后兼容的新ID生成器。在persistence.xml文件中将此属性设置为false将恢复旧的ID生成器行为。

hibernate 4文档还包含有关新ID生成器的信息:http://docs.jboss.org/hibernate/core/4.0/manual/en-US/html_single/#mapping-declaration-id-generator

hibernate文档明确指出默认情况下不启用新的ID生成器,但如上所述,JBoss 7.1会自动启用它们。

答案 2 :(得分:22)

hibernate.id.new_generator_mappings中将false设置为persistence.xml只是问题解决方案的第一部分:

为了彻底解决问题,我在allocationSize(我省略了)中添加了1@SequenceGenerator