【问题标题】:Seam-managed transactions how-toSeam 管理的事务操作方法
【发布时间】:2010-07-15 14:12:31
【问题描述】:

Seam 建议在 Stateful 会话 Bean 中使用 Extended 持久性上下文,以便拥有 Seam 管理的持久性。

我不清楚上述建议是否会对我们希望拥有 Seam 管理的事务的方式产生任何影响。这是因为我们的架构不同。我们在 Stateless EJB 中有以下持久性上下文:

@Stateless
@TransactionAttribute(TransactionAttributeType.REQUIRED)
public class CrudServiceBean implements CrudService {

    @PersistenceContext(type = PersistenceContextType.TRANSACTION)
    private EntityManager em;
...
}

我们的 DAO 调用上述 CrudServiceBean 是无状态 EJB(其中一些也是 Seam 组件),带有 @TransactionAttribute(TransactionAttributeType.REQUIRED)。因此,我们的事务由容器(WebLogic)处理,而不是Seam。

但是,我们现在需要满足以下场景:我们需要有一个前端 Seam 组件(非 EJB)调用多个 DAO (EJB) 方法并将它们全部包装在一个单笔交易。如果我理解正确,我们需要有 Seam 管理的事务。

我们可以像我描述的场景那样拥有 Seam 管理的事务,而没有 Seam 管理的持久性上下文吗?还是两者无关?

【问题讨论】:

    标签: java transactions weblogic seam bean-managed-transactions


    【解决方案1】:

    如你所说

    我们需要有一个前端 Seam 组件(非 EJB)调用多个 DAO (EJB) 方法并将所有这些方法包装在一个事务中

    但是

    我们的事务由容器处理 - 也称为容器管理事务(容器负责调用每个底层资源管理器事务使用的开始和提交方法)

    第一个问题是您有一个非 EJB 调用多个 DAO 的场景,每个 DAO 都是一个 EJB。你可以想到

    @Name("nonEjbComponent")
    public class NonEjbComponent {
    
        private @In DaoEjbComponent daoEjbComponent;
        private @In OtherDaoEjbComponent otherDaoEjbComponent;
        private @In AnotherDaoEjbComponent anotherDaoEjbComponent;
    
        private @In UserTransaction userTransation;
    
        public void wrapperAllOfThem() {
    
             userTransation.begin();
    
                 daoEjbComponent.save(someEntity);
                 otherDaoEjbComponent.update(otherEntity);
                 anotherDaoEjbComponent.delete(anotherEntity);
    
             userTransation.commit();
    
        }
    
    }
    

    但 Java EE 规范 3.0 规定

    具有 bean 管理或容器管理事务分界的企业 bean必须是会话 bean 或消息驱动 bean

    所以你不能使用上面的场景。而且由于您的所有 DAO 都使用容器管理的事务,Java EE 规范不允许您使用容器管理和 bean 管理的事务同时

    所以解决办法是

    将所有 DAO 包装在一个 EJB 无状态会话 bean 其事务由容器管理。它的行为就像一个委托组件

    @Stateless
    @TransactionAttribute(TransactionAttributeType.REQUIRED)
    @Name("wrapperStateless")
    public class WrapperStatelessImpl implements WrapperStateless {
    
        private @In DaoEjbComponent daoEjbComponent;
        private @In OtherDaoEjbComponent otherDaoEjbComponent;
        private @In AnotherDaoEjbComponent anotherDaoEjbComponent;
    
        public void wrapperAllOfThem() {
    
            daoEjbComponent.save(someEntity);
            otherDaoEjbComponent.update(otherEntity);
            anotherDaoEjbComponent.delete(anotherEntity);
    
        }
    
    }
    

    在你的非 EJB 组件中,使用

    @Name("nonEjbComponent")
    public class NonEjbComponent {
    
        private @In WrapperStateless wrapperStateless;
    
        public void wrapperAllOfThem() {
            wrapperStateless.wrapperAllOfThem();
        }
    
    }
    

    【讨论】:

    • 我只是想了解这里。这是否意味着如果我有非 EJB 接缝组件,接缝无法管理事务,我必须遵循此处描述的类似模式?
    猜你喜欢
    • 2018-09-14
    • 2012-08-13
    • 1970-01-01
    • 1970-01-01
    • 2012-04-13
    • 1970-01-01
    • 1970-01-01
    • 2022-11-30
    • 2011-10-01
    相关资源
    最近更新 更多