2016-05-30 34 views
2

我一直遇到实体管理器merge()方法的问题。HibernateException:foo实例的标识符已从X更改为Y

有两个实体'FOO'和'BAR',它们在模式中没有关系,只能保持这种方式,可悲的是我不能改变它。 FOO中有一个名为PROCESS_CD的列,与BAR中的CLASS_CD完全相同。 CLASS_CD是BAR的主键,但FOO中的PROCESS_CD不是外键。

我想将PROCESS_CD中FOO的值从X更新为Y,但是hibernate会尝试更改BAR中的值,从而发生错误。

我不知道如何指定它应该在FOO只更新而不是在BAR

因此,这里是我的数据库架构

Database Schema

我的Foo类

@javax.persistence.Entity 
@Table(name = "FOO") 
public class FooImpl implements Foo { 

    private Long callCode; 
    private Journal journal; 

    @Id 
    @Column(name = "CALL_CD") 
    public Long getCallCode() { 
     return callCode; 
    } 

    public void setCallCode(Long aLong) { 
     callCode = aLong; 
    } 


    @ManyToOne(fetch = FetchType.LAZY, targetEntity = BarImpl.class) 
    @JoinColumn(name = "PROCESS_TYPE") 
    public Journal getJournal() { 
     return journal; 
    } 
} 

我的酒吧班

@javax.persistence.Entity 
@Table(name = "BAR") 
public class BarImpl implements Bar { 

    private String Code; 
    private String Description; 

    public List<Interaction> interaction; 

    @Id 
    @Column(name = "CLASS_CD") 
    public String getCode() { 
     return Code; 
    } 

    public void setCode(String code) { 
     Code = code; 
    } 

    @Column(name = "CLASS_LONG_DESCR") 
    public String getDescription() { 
     return Description; 
    } 

    public void setDescription(String description) { 
     Description = description; 
    } 
} 

这是我fooDao类

public class FooDao { 

    public void saveFoo(Foo instance) { 
     log.debug("update instance"); 
     try { 
      if (getEntityManager().contains(instance)) { 
       getEntityManager().merge(instance); 
      } else { 
       getEntityManager().persist(instance); 
      } 
      log.debug("update successful"); 
      return instance; 
     } catch (RuntimeException re) { 
      log.error("update failed", re); 
      throw re; 
     } 
    } 

    public void startTransaction() throws TransactionException{ 
     EntityTransaction t = getEntityManager().getTransaction(); 
     t.begin(); 
     TransactionManager.setTransaction(t); 
    } 
    public void commitTransaction()throws TransactionException { 
     EntityTransaction t = TransactionManager.retrieveTransaction(); 
     if(t == null) 
      throw new TransactionException("No transaction associated witht his thread"); 
     t.commit(); 
    } 
    public void rollbackTransaction() throws TransactionException{ 
     EntityTransaction t = TransactionManager.retrieveTransaction(); 
     if(t == null) 
      throw new TransactionException("No transaction associated witht his thread"); 
     t.rollback(); 
    } 
} 

,然后最后我打电话的方式来保存

以下是错误我得到

Caused by: org.hibernate.HibernateException: identifier of an instance of BarImpl was altered from X to Y 

我希望你能帮忙,我可以” t找到任何东西在国际

谢谢你的时间

+0

嗯还是找不到问题 – SandMan

回答

0

首先感谢大家回复我的问题,你们都非常有用。 :D

我发现我的问题,它与我的实际实施居住。我不是创建一个新的barImpl,而是去搜索一个,如果它是空的,它需要创建一个新的bar,但是如果它找到一个,它会继续并输入新的值。

请参阅我不知道实体类与数据库中的实际记录保持关系。所以当我改变DAO发现的实体的值时,实际上是在尝试保存foo实体时尝试更改数据库中的值。

祝你有个愉快的日子