Oracle Trigger的HIbernate问题,用于从序列生成id

RKo*_*dla 8 oracle triggers hibernate spring-mvc sequence

我们有一个before insert触发器,它从序列中获取下一个值.当使用save()方法持久化对象时,hibernate从序列中获取值并将其添加到对象中.当从Spring的服务层提交事务时,数据库上的ID值再次增加.如果对象已经有id,我该如何避免获取nextval()..

这是我想要做的......

userDAO的

public User saveUser(User user){
      session.getCurrentSession.save(user);//line2
      return user;//line3  
 }
Run Code Online (Sandbox Code Playgroud)

UserService

public void saveUserAndWriteToAudit(User user, UserAudit userAudit){
  userDao.saveUser(user);//line1
  userAudit.setUserId(user.getId);//line4
  userAudit.saveUserAudit(userAudit);//line5
}
Run Code Online (Sandbox Code Playgroud)

和用户类

 @Entity
  public class User{

     @Id
     @GeneratedValue(strategy=GenerationType.AUTO, generator="a1")
     @SequenceGenerator(name="a1", sequenceName="usersequence")
     private Long id;
     /////////////////
 }
Run Code Online (Sandbox Code Playgroud)

当光标到达line1和line2时,用户对象在id属性中为null.在line2之后,它有来自序列的nextval - 让我们说1.在第4行,我已将用户的id = 1添加到useraudit对象..当事务在第5行之后提交时,2被插入到User的id列中,1被插入到UserAudit的userId列中.这对我没有任何意义:(我该如何避免这个问题?谢谢!

Mat*_*son 11

只需将触发器更新为仅在未给出id时触发.

create or replace
trigger sa.my_trigger
before insert on sa.my_table
for each row
when (new.id is null)
begin
   select sa.my_sequence.nextval
    into :new.id
    from dual;
end;
Run Code Online (Sandbox Code Playgroud)


Chr*_*ang 5

上面的解决方案很棒,它为这个问题省去了很多麻烦.

我唯一的抱怨是打开用户/代码的大门,插入任何ID值而不实际查询序列.

我发现以下解决方案也有效.它允许Hibernate找到最大ID,并在每次执行insert语句时使其递增.但是当它到达数据库时,ID被忽略并被触发器生成的ID替换,因此群集问题中没有唯一性:

    @Id
    @GeneratedValue(generator="increment")
    @GenericGenerator(name="increment", strategy = "increment")
    private Long id;
Run Code Online (Sandbox Code Playgroud)

最大的缺点是@GenericGenerator是一个Hibernate注释,因此你失去了JPA的可移植性.程序员也不清楚这个ID实际上是否与序列相关联,而事实上,它是使用序列的最紧密耦合解决方案之一.