JPA主键自动生成
我的主要密钥实体如下所示
@GeneratedValue(strategy= GenerationType.TABLE) private Long id;
当我跑,我得到错误
无法获取或更新下一个值;嵌套exception是org.hibernate.exception.SQLGrammerException:无法获取或更新下一个值
但是当我改变的时候
@GeneratedValue private Long id;
没有错误抛出。 我想在oracle db上为每个表生成唯一的主键。
@GeneratedValue(strategy=GenerationType.TABLE)
告诉JPA提供程序在将新创建的实体插入数据库时使用表来获取ID。
当使用Hibernate作为提供者时,这将产生一个表hibernate_sequences
,它有两列:实体名称和已分配给该实体的最大标识。 在这里,似乎Hibernate没有成功为你的实体获取它的下一个ID,但很难说确切原因,因为你没有提供足够的信息。
那么,你能提供完整的堆栈跟踪吗? 另外,请将hibernate.show_sql
属性设置为true
并将日志设置为log4j.logger.org.hibernate.SQL=DEBUG
。 如果可能,请将日志加入您的问题。
也许只是检查一下你是否为Oracle配置了正确的hibernate.dialect
。 实际上,如果可能的话,也加入你的hibernate配置。
PS:使用Oracle生成PK的“传统”方法是使用序列(您可以让Hibernate使用GenerationType.AUTO
为您的数据库类型猜测最佳策略或使用SEQUENCE
强制它)但我假设您需要结果数据结构是数据库不可知的。 如果没有,我建议改用序列。
编辑:回答OP关于GenerationType.AUTO
的评论。 实际上,默认值是一个名为hibernate_sequence
的单个全局序列,这可能是个问题。 但是,通过下面显示的设置,您可以使用GenerationType.AUTO
并仍然控制数据库使用序列的情况下序列的名称:
@Id @GeneratedValue(strategy=GenerationType.AUTO, generator="my_entity_seq_gen") @SequenceGenerator(name="my_entity_seq_gen", sequenceName="MY_ENTITY_SEQ") private long id;
换句话说,您可以使用为每个表使用不同的序列名称而不会丢失可移植性。
JPA中有4种自动生成策略:
- 汽车
- 身分
- 序列
- 表
对于Oracle自动生成主键注释,可以选择Sequence和Table。 基本逻辑是首先定义生成器,分别使用@SequenceGenerator或@TableGenerator ,然后在@GeneratedValue中使用生成器作为属性。
这是如何使用序列策略的示例:
@Id @SequenceGenerator(name="SEQ_GEN", sequenceName="SEQ_JUST_FOR_TEST", allocationSize=1) @GeneratedValue(strategy=GenerationType.SEQUENCE, generator="SEQ_GEN") private long id;
以下是如何使用表策略的示例:
@Id @TableGenerator(name="TABLE_GEN",table="T_GENERATOR", pkColumnName = "GEN_KEY", pkColumnValue = "MONITOR2012.T_JUST_FOR_TEST", valueColumnName = "GEN_VALUE", initialValue = 1, allocationSize = 1 ) @GeneratedValue(strategy = GenerationType.TABLE, generator="TABLE_GEN") private long id;
如果@GeneratedValue注释中没有指定生成器,则选择将留给JPA实现。
如果您正在使用现有表的数据库,请确保在运行应用程序之前在数据库中定义序列或表。 在@GeneratedValue注释可以正常工作之前,表生成器还需要您在表中插入一行。
以下是有关如何在JPA for Oracle数据库中配置主键自动生成的教程。
- 为什么hibernate执行两个查询以急切加载@OneToOne双向关联?
- 使用Hibernate映射数组
- Hibernate,MySQL Views和hibernate.hbm2ddl.auto = validate
- 在独立应用程序中的hibernate中配置sessionFactory
- Hibernate – 将java.util.Calendar映射到MySQL BIGINT
- Hibernate 4使用java.time.LocalDate和DATE()构造
- 什么是与Hibernate和JDBC相关的对象/关系映射(ORM)?
- 如何使用Hibernate插入新项目?
- Hibernate hbm2ddl.auto默认值