Wildfly - @TransactionAttribute -

时间:2017-02-21 22:41:32

标签: java hibernate jboss transactions wildfly

在我的Wildfly 10项目中,java 8,mysql,camel和hibernate

methodKO持久化实体orderEntity(“ko”),调用methodOK并进入异常; methodOK持久化实体orderEntity(“ok”)

尽管在methodKO中有异常,我想在db中找到orderEntity(“ok”),所以我用@TransactionAttribute(TransactionAttributeType.REQUIRES_NEW)注释了methodOK 但这不起作用

此处有关配置文件的详细信息:

独立-全ha.xml:

<datasources>
<xa-datasource jndi-name="java:jboss/datasources/myDS" pool-name="myDS" enabled="true" use-ccm="true">
....
</datasources>

的persistence.xml:

<persistence-unit name="camel" transaction-type="JTA">
<jta-data-source>java:jboss/datasources/myDS</jta-data-source>
....

为myBean:

@Stateless
public class MyBean {
    @Inject
    OrderDAO orderDAO;

    private void methodKO() throws Exception {
        orderDAO.create(new orderEntity("ko"));
        methodOK();
        throw new Exception("err");
    }

    @TransactionAttribute(TransactionAttributeType.REQUIRES_NEW)
    private void methodOK() {
        orderDAO.create(new orderEntity("ok"));
    }

}

2 个答案:

答案 0 :(得分:0)

根据EJB 3.1:

  

事务属性是与每个属性相关联的值   以下方法:

     

a)bean的业务接口的方法

     b)通过该方法暴露的方法   bean类无接口视图

这意味着私有方法上的任何Transactional注释都是无用的。

我会将这两种方法定义为 public

@Stateless

public class MyBean {
    @Inject
    OrderDAO orderDAO;

    public void methodKO() throws Exception {
        orderDAO.create(new orderEntity("ko"));
        methodOK();
        throw new Exception("err");
    }

    @TransactionAttribute(TransactionAttributeType.REQUIRES_NEW)
    public void methodOK() {
        orderDAO.create(new orderEntity("ok"));
    }

}

这个bean实现一个实际上包含这两个方法的接口将是一个很好的做法。

答案 1 :(得分:0)

首先,抛出已检查的异常通常不会触发事务回滚,除非您在特定的Exception类型上使用@ javax.ejb.ApplicationException(rollback = true)专门为此配置。未经检查的异常默认触发回滚。

由于Maciej很好地描述的原因,您需要改变尝试实现此逻辑的方式。有两种方法可以实现您想要的行为:

丑陋的方式:

@Stateless
public class MyBean {

    @Resource
    private SessionContext sessionContext;

    @Inject
    OrderDAO orderDAO;

    public void methodKO() throws Exception {
        orderDAO.create(new orderEntity("ko"));
        sessionContext.getBusinessObject(MyBean.class).methodOK();
        throw new RuntimeException("err");
    }

    @TransactionAttribute(TransactionAttributeType.REQUIRES_NEW)
    public void methodOK() {
        orderDAO.create(new orderEntity("ok"));
    }

}

整洁的方式:

@Stateless
public class MyBean {

    @Inject
    OrderDAO orderDAO;

    public void methodKO() throws Exception {
        orderDAO.create(new orderEntity("ko"));
    }

    @TransactionAttribute(TransactionAttributeType.REQUIRES_NEW)
    public void methodOK() {
        orderDAO.create(new orderEntity("ok"));
    }

}


@Stateless
public class MyBusinessBean {

    @Inject
    private MyBean myBean;

    public void businessMethod() {
        myBean.methodKO();
        myBean.methodOK();
        throw new RuntimeException("Trip rollback");
    }
}