为什么会话bean方法在抛出RuntimeException时抛出EjbTransactionRolledbackException

时间:2010-09-25 11:45:26

标签: java java-ee-6 jpa-2.0 ejb-3.1 bean-validation

我试图通过约束验证来持久化实体, 当调用持久化时 - 抛出约束并且调用者获得EjbTransactionRolledbackException ... 所以我尝试显式调用验证并抛出ConstraintViolationException / RuntimeException,然后调用者得到EjbTransactionRolledbackException ... 当我抛出MyException延伸Exception时 - 来电者获得MyException

即使我称之为明确的sc.setRollBackOnly,它仍然会发生:(

这不应该是行为。

发生了什么事?

配置:

Netbeans 6.9.1 Glassfish 3.0.1 JPA 2.0(EclipseLink) EJB 3.1

感谢!!!

@Stateless
public class My {

@PersistenceContext
EntityManager em;

@Resource
Validator  validator;

public Order checkout(Order order) {
    Set<ConstraintViolation<Order>> set = validator.validate(order, Default.class);

    if (!set.isEmpty()) {
        sc.setRollbackOnly();
        //throw new ConstraintViolationException(new HashSet<ConstraintViolation<?>>(set));
        throw new RuntimeException();
    }

    this.em.persist(order);
}

2 个答案:

答案 0 :(得分:10)

  

所以我尝试显式调用验证并抛出ConstraintViolationException / RuntimeException,然后调用者仍然得到EjbTransactionRolledbackException ......

提供完整的堆栈跟踪可能会有所帮助。无论如何,我想知道你是如何调用EJB的,如果你正在传播一个事务,在这种情况下抛出EJBTransactionRolledbackException是系统异常的正确行为。但是以下博文可能有所帮助:

  

Constraint violated, transaction rolled back

     

在JPA上使用bean验证时   EJB 3 bean中的实体   实际上会得到一个   EJBTransactionRolledbackException if   存在约束违规。

javax.ejb.EJBTransactionRolledbackException: Invalid object at persist time for groups [javax.validation.groups.Default, ]
Caused by: javax.validation.ConstraintViolationException: Invalid object at persist time for groups [javax.validation.groups.Default, ]
     

这一切都很好   规范,但不是真的   有趣的信息。你没有   真的很想知道发生了什么事,你   想知道出了什么问题。

     

所以我建议添加以下内容   你的ejb-jar.xml:

<?xml version="1.0" encoding="UTF-8"?>
<ejb-jar
        xmlns="http://java.sun.com/xml/ns/javaee"
        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xsi:schemaLocation="http://java.sun.com/xml/ns/javaee
                            http://java.sun.com/xml/ns/javaee/ejb-jar_3_0.xsd"
        version="3.0">
   <assembly-descriptor>
      <application-exception>
         <exception-class>javax.validation.ConstraintViolationException</exception-class>
         <rollback>true</rollback>
      </application-exception>
   </assembly-descriptor>
</ejb-jar>
     

这样你就可以直接访问你的   违规。

资源

答案 1 :(得分:0)

只需集成@Pascal的答案,还可以用

标记Exception(如果它是您自己的)
 @javax.ejb.ApplicationException(rollback = true)
 public class UncheckedException extends RuntimeException {...}