JPA事务回滚失败,调用无状态bean

在BMT内部(使用UserTransaction)我在另一个无状态EJB上调用一个方法.当我回滚此事务时,不会回滚在EJB方法中创建的实体.我将EJB 3.1与JPA 2.0一起使用.事务以方法doTheTransaction()开头:

@Stateless
@LocalBean
@TransactionManagement(TransactionManagementType.BEAN)
public class TaskExecutor {

    @Inject private SomeEntityFacade someEntityEJB;
    @Inject private RandomEJB randomEJB;
    @Resource private UserTransaction ut;

    @Asynchronous
    public Future<String> doTheTransaction () { // we start here

        try {
            SomeEntity someEntity = new SomeEntity();
            someEntityEJB.create(someEntity); // this entity is rolled back

            // call another EJB to create a SomeEntity, this entity is not rolled back
            randomEJB.createSomeEntity();

            // cause error for test
            int i = 5 / 0;

            ut.commit();
        } catch (java.lang.ArithmeticException e) {
            ut.rollback();
        }
    }
    // Omitted exceptions thrown by UserTransaction methods because they give no problems
}

RandomEJB:

@Stateless
@LocalBean
@TransactionManagement(TransactionManagementType.BEAN)
public class RandomEJB {

    @Inject private SomeEntityFacade someEntityEJB;

    public void createSomeEntity () {
        // same code to create entity as in TaskExecutor:
        SomeEntity someEntity = new SomeEntity();
        someEntityEJB.create(someEntity);
    }
}

要完成,这是SomeEntity的基本部分:

@Stateless
@LocalBean
public class SomeEntityFacade {

    @PersistenceContext(unitName = "com.mysite.PU")
    private EntityManager em;

    public void create (SomeEntity p_someEntity) {
        em.persist(p_someEntity);
    }

如果您有兴趣,这是我的persistence.xml:

<?xml version="1.0" encoding="UTF-8"?>
<persistence version="2.0" xmlns="http://java.sun.com/xml/ns/persistence" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/persistence http://java.sun.com/xml/ns/persistence/persistence_2_0.xsd">
    <persistence-unit name="com.mysite.PU" transaction-type="JTA">
    <jta-data-source>jdbc/myDatabase</jta-data-source>
    <properties></properties>
    </persistence-unit>
</persistence>

为什么在RandomEJB中创建的实体没有回滚,而直接在事务中创建的实体是?

也许this post是相关的,但我真的不明白给出的答案.

编辑:发现错误:使用@TransactionManagement(TransactionManagementType.BEAN)注释RandomEJB.我的理解是BMT事务不会通过其他BMT注释方法传播,而是创建新事务.当初始事务可能失败并回滚时,那个可以成功.我猜你在使用BMT / CMT注释方法时需要小心.有人能证实吗?

最佳答案
就像你说的那样–BMT bean并没有彼此分享交易.

这意味着您无法重用在另一个BMT中明确启动的事务. BMT就像“我知道游戏的内容,我将自己管理交易内容”.

所以:

> BMT – > BMT不会分享交易
> BMT – > CMT将共享交易(CMT将使用实际交易 – 它不关心它是否是容器启动或用户启动 – 它只是对交易存在感兴趣).

转载注明原文:JPA事务回滚失败,调用无状态bean - 代码日志