来自Java Persistence with Hibernate(Manning,2007)p。 419:
我应该在Session上使用persist()吗? Hibernate Session接口 还有一个persist()方法。它具有与之相同的语义 JPA的persist()操作。但是,有一个重要的区别 关于冲洗的两个操作之间。中 同步,Hibernate Session不会级联persist() 对相关实体和集合的操作,即使您已映射 与此选项的关联。 它只与实体级联 当你调用persist()时可以访问!只有save()(和update()) 如果使用Session API,则在刷新时级联。在JPA中 然而,应用程序是相反的:只有persist()才是 在冲洗时级联。
这种难以理解的措辞......这意味着“当你呼叫坚持时可以到达的实体()”是什么意思?
如果我更新了关联实体,那么它是否应该“无法访问”?
另外......如果它是session.persist()行为的一部分,那为什么它不在javadoc?
答案 0 :(得分:0)
我真的不知道这是不是真的,但我至少可以解释它的含义。
假设您有以下实体:
public class Order {
@OneToMany(cascade = PERSIST)
private List<OrderLine> lines;
// ...
}
并执行以下操作:
Order order = new Order();
session.persist(order);
OrderLine line = new OrderLine();
order.addLine(line);
session.flush(); // the flush could also be called implicitely, when committing or executing a query
根据您问题中的文字,该行不会被保留,因为调用persist(order)
时订单无法访问:此时,该行不在订单呢。
另一方面,您是否使用实体管理器:
Order order = new Order();
em.persist(order);
OrderLine line = new OrderLine();
order.addLine(line);
em.flush(); // the flush could also be called implicitely, when committing or executing a query
然后该行将被保留,因为当实体的状态与数据库同步时,它可以从刷新时的订单到达。
答案 1 :(得分:0)
Hibernate的EntityManager实现是:
org\hibernate\hibernate-entitymanager\4.3.5.Final\hibernate-entitymanager-4.3.5.Final-sources.jar!\org\hibernate\jpa\spi\AbstractEntityManagerImpl.java
这是persist()方法
@Override
public void persist(Object entity) {
checkOpen();
try {
internalGetSession().persist( entity );
}
catch ( MappingException e ) {
throw convert( new IllegalArgumentException( e.getMessage() ) ) ;
}
catch ( RuntimeException e ) {
throw convert( e );
}
}
所以JPA persist(实体)实际上是在调用org.hibernate.internal.Session.persist(entity)。
因此,在持久化实体方面,JPA和Hibernate之间不应该有任何区别。
它只与您通话时可以访问的实体级联 坚持()!
2007年,Hibernate 3.2已经发布,3.3版本正在发布。那时候JPA was only a draft:
您也可以使用persist()而不是save(),并使用EJB3中定义的语义&gt; &GT; &GT;提前选秀。
但根据文件:
如果将父级传递给persist(),则会传递所有子级 坚持()
对于JPA,级联persist()是有意义的,因为根本没有save()操作。但当时人们正在使用save(),saveOrUpadet()甚至saveOrUpdateCopy(),这些都被弃用,而选择了persist()和merge()。
当时,持久的JPA定义只是一个草案,因此特定的实现并未反映出明确的特征。