我有使用Hibernate写入Oracle表的代码。它使用SequenceGenerator生成唯一的id。假设我在数据库中有id 1到40。如果从表中删除任何用户,它会在表中的id中留下间隙(例如,id = 24)。然后,当创建新用户时,新用户的id由Hibernate设置为24.
现在有一个问题,因为下一个新用户立即获得id = 25,这会导致UniqueConstraint异常。
我做错了吗?如何使Hibernate停止生成表中已存在的序列值?
@Entity
@Table(name="User")
public class User {
@Id
@SequenceGenerator(name="UserGen", sequenceName="UserSeq")
@GeneratedValue(strategy=GenerationType.SEQUENCE, generator="UserGen")
private Integer id;
@Column(length=64, unique=true)
private String username;
...
以下是Oracle中的序列信息:
CREATED 31-OCT-16
LAST_DDL_TIME 31-OCT-16
SEQUENCE_OWNER USERSERVICE
SEQUENCE_NAME USERSEQ
MIN_VALUE 1
MAX_VALUE 9999999999999999999999999999
INCREMENT_BY 1
CYCLE_FLAG N
ORDER_FLAG N
CACHE_SIZE 20
LAST_NUMBER 81
PARTITION_COUNT
SESSION_FLAG N
KEEP_VALUE N
答案 0 :(得分:1)
您必须将SequenceGenerator
定义为与序列的allocationSize
值具有相同的INCREMENT_BY
。
@SequenceGenerator(name="UserGen", sequenceName="UserSeq", allocationSize = 1)
我之前(在PostgreSQL中)遇到过这个问题,最后我把它改为@GeneratedValue( strategy = GenerationType.IDENTITY )
并完全删除了SequenceGenerator
,因为它们在未指定时已被用作插入时的默认值。当序列增量大小为1时,这会略微提升性能,因为SequenceGenerator
Hibernate会手动调用序列,使用一个可以备用的额外查询。