我有两个表(即Hibernate中的实体),它们相关如下:

@Entity
@Table(name = "table_one")
public class TableOne  {

    private int id;
    private String code;
    private String value;

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Column(name = "id", unique = true, nullable = false)
    public Integer getId() {
        return this.id;
    }

    @Column(name= "code")
    public String getCode() {
        return this.code;
    }

    @Column(name= "value")
    public String getValue() {
        return this.value;
    }
    // setters ignored here
}

----------------------------------------------
@Entity
@Table(name = "table_two")
public class TableTwo {

    private Integer id;
    private TableOne tableOne;
    private String request;

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Column(name = "id", unique = true, nullable = false)
    public Integer getId() {
        return id;
    }

    @ManyToOne(fetch = FetchType.EAGER)
    @JoinColumn(name = "table_one_id", nullable = false)
    public TableOne getTableOne() {
        return tableOne;
    }

    @Column(name= "request")
    public String getRequest() {
        return this.request;
    }
    // setters ignored here
}


现在,从没有@Transactional批注的方法(或类)中,我调用Service类方法来持久化TableTwo对象。此服务方法带有@Transactional注释。

// from a normal method with no annotations
service.insert(tableTwo);
----------------------------
public class MyService {

    @Autowired
    private MyDao dao;

    @Transactional
    public void insert(TableTwo tableTwo){
        dao.insert(tableTwo);
    }
}
------------------------------
public class MyDao {
    public void insert(TableTwo tableTwo){
      sessionFactory.getCurrentSession().persist(tableTwo.getTableOne());
      sessionFactory.getCurrentSession().persist(tabletwo);
    }
}


这给了我以下调试异常:

Method threw 'org.hibernate.PersistentObjectException' exception.
detached entity passed to persist: org.project.TableOne


这是怎么了?我将TableOne中的TableTwo瞬态对象转换为持久状态,然后持久化TableTwo对象。我该如何纠正呢?如果可能的话,可以通过注释吗?

我不想每次持久化TableOne对象时都持久化TableTwo对象。如果可能,我只想做:

tableTwo.setTableOne(new TableOne(id));
dao.persist(tableTwo);

最佳答案

我看到您正在从服务类即tableOne获取TableOne tableOne = service.getTableOneById(id);对象。

因此,我相信tableOne记录已存在于数据库中,因此以后无需再次将其保存在dao insert(...)方法中。

您可以删除sessionFactory.getCurrentSession().persist(tableTwo.getTableOne());,因为您没有对tableOne对象进行任何更改。

或者,如果您需要保留对tableOne对象的任何更改,请考虑使用合并方法,即sessionFactory.getCurrentSession().merge(tableTwo.getTableOne());

10-06 11:24