JPA添加或更新对象

时间:2012-11-04 08:48:32

标签: jpa eclipselink

我正在尝试使用EclipseLink保存一个名为Stat的对象。如果db中存在id,则更新该对象。如果没有,请创建一个新对象。这是我的目标:

@Entity
public class Stat {

    @Column
    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    public long id;

    @JoinColumn
    @ManyToOne
    public User user;


    @Column
    public boolean accepted;

    @Column
    public boolean finished;

    public Stat() {
    }
}

这是我添加/更新对象的方法。

public long addReplaceStat(Stat stat) {
            em.getTransaction().begin();
            Stat oldStat = em.find(Stat.class, stat.id);
            if (oldStat == null)
                em.persist(stat);
            else
                em.merge(stat);
            em.getTransaction().commit();

            em.getTransaction().begin();
            Stat newStat = em.find(Stat.class, stat.id);
            if (newStat != null)
                em.refresh(newStat);
            em.getTransaction().commit();

            return stat.id;
        }

我的问题是我在em.refresh()处得到异常,说“类[User]的属性[id]被映射到数据库中的主键列。不允许更新。”我不明白为什么。不刷新只是更新我的托管对象的值而没有问题吗?

做我想做的最好的成语(添加或更新)是什么?

1 个答案:

答案 0 :(得分:3)

JPA规范说:

  

应用于实体X的合并操作的语义为   如下:

     
      
  • 如果X是分离的实体,则将X的状态复制到具有相同标识的新预先存在的托管实体实例X'或新的   X的托管副本X'已创建。
  •   
  • 如果X是新的实体实例,则创建新的托管实体实例X',并将X的状态复制到新的托管实体中   实例X'。
  •   
     

[...]

所以要添加,如果不存在或更新它是否存在,你只需要这样做:

Stat attachedStat = em.merge(stat);

关于刷新问题,我不知道为什么会这样。但是,为什么要刷新刚从数据库加载的实体?没有什么可以刷新的。