我有一个定义如下的类:
@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开始,然后向上)
知道为什么会这样吗?
5条答案
按热度按时间deikduxw1#
新行为如下:
seq.nextval
。因此,您必须在
allocationSize
(Hibernate)和序列increment by
(DB)上声明相同的值显式设置
allocationSize=500
时,例如在Oracle上否则,您将注意到由于主键冲突而从DB中引发的负值或约束错误。
当应用服务器重新启动时,您会注意到最近分配的主键和重新启动时选择的“新”序列号之间的“跳转”。
最终意见:因此,如果您不在Hibernate端指定
allocationSize
,您必须在DB端声明increment by
50。qnakjoqk2#
我刚刚在从JBoss 6.1迁移到JBoss 7.1时遇到了这个问题。
根据JBoss AS 7.1 JPA文档(https://docs.jboss.org/author/display/AS71/JPA+参考+指南#JPA参考指南-持久性单元属性),
JBoss 7.1会自动设置多个休眠属性。其中一个要设置的属性是
hibernate.id.new_generator_mappings
,它会激活使用不同算法且不向后兼容的新ID生成器。在persistence.xml文件中将此属性设置为false将恢复旧的ID生成器行为。hib4文档还包含有关新ID生成器的信息:www.example.com网站。http://docs.jboss.org/hibernate/core/4.0/manual/en-US/html_single/#mapping-declaration-id-generator.
hib文档明确指出,默认情况下不启用新的ID生成器,但是如上所述,JBoss 7.1会自动启用它们。
hc2pp10m3#
在我的
persistence.xml
中将hibernate.id.new_generator_mappings
设置为false
只是解决我的问题的第一部分:为了完全解决这个问题,我在
@SequenceGenerator
中添加了allocationSize
到1
(我省略了)。bvjveswy4#
我们遇到了一个类似的错误,但原因(可能)不同:
我们没有显式定义
allocationSize
(因此使用默认值50
)。我们运行了应用程序,但删除了数据库并重新创建了它。Hibernate使用了它的id缓存,然后与数据库通信以获得新的id。现在hibernate-id缓存至少是50(对于某些表可能要高得多),但是数据库被删除,重建,现在是空的,所以已经有一些不一致了...但是不管什么原因hib在-48开始了下一轮的id。
我们遇到了一个后续错误,因为我们的实体的ID定义为数据类型
int
而不是Integer
,当hib继续计数并到达0
的实体时,它认为它还没有在数据库中,试图创建INSERT
而不是UPDATE
,并得到了一个密钥验证错误。我仍然不能解释为什么hib在遇到这种不一致的情况下决定从
-48
开始键...但是对于我们来说,在改变数据库中的序列之前,简单地关闭应用程序就可以解决这个错误。而且我们所有的实体现在都使用Integer
代替int
作为id。希望这些信息对外面的人有帮助。
jfgube3f5#
谢谢!!!添加下面的代码后工作正常