我的应用程序使用Hibernate作为JPA提供程序,使用JBOSS 6.1.0-final作为服务器。事务是CMT(我的persistence.xml中的事务类型是JTA)。正如大多数教程所说。 ejb方法中的事务将在没有任何异常的情况下自动提交。但是,在我的应用程序中,除非我使用flush()
,否则当ejb方法成功结束时(例如,插入记录从不将任何数据推送到数据库),将不会提交事务。无状态和有状态bean都是相同的结果。
我尝试使用@TransactionAttribute(TransactionAttributeType.REQUIRED)
,但结果也一样。即使使用MANDATORY
注释也不会抛出任何异常,这表明我的ejb方法正在使用容器管理的事务。
Code Fragement:
@Stateful
@Local
public class TransactionTest implements ITransactionTest {
@PersistenceContext(unitName="Table")
private EntityManager manager;
public void generateRecord(int i) throws RuntimeException{
Record record = new Record();
record.setId(i+"");
record.setStatus(1);
manager.persist(record);
manager.flush(); //without this, it won't commit
}
}
那么,为什么我的ejb方法不能自动提交事务呢?
答案 0 :(得分:1)
默认状态会话bean有PersistenceContextType.EXTENDED
。
5.6.1.2容器管理的扩展持久化上下文
从那时起,就存在容器管理的扩展持久化上下文 已获得容器管理的实体管理器 依赖注入或通过JNDI查找,直到它被关闭 容器。只能启动这种扩展的持久化上下文 在有状态会话bean的范围内,并由关闭 容器当有状态会话bean的@Remove方法时 完成(或者有状态会话bean实例) 破坏)。
使用扩展持久性上下文时,实体 由EntityManager管理的是否独立于是否进行管理 JTA交易已开始或已提交。他们不会脱离 直到持久化上下文结束。
您可以尝试TransactionAttributeType.REQUIRES_NEW
,因此在退出方法后调用commit。在提交之前自动调用Flush。
如果您想立即提交更改,可以尝试更改交易属性,该属性将成为单独新交易的一部分。
如果您不想提交更改&需要单一交易来传播,那么你目前的方法是好的和明确地打电话。