当前位置: 首页 > 知识库问答 >
问题:

如何在WebSphere 8.0上获得TransactionManager?

谭池暝
2023-03-14

我试图在@Singleton SessionBean(EJB 3.1)中获取TransactionManager来控制我的事务范围,因为我必须通过@PostConstruct方法访问数据库。如果发生html" target="_blank">异常,我不能让容器回滚,因为它会引发TransactionRolledbackException:setRollbackOnly,只从单例后期构造方法中调用。

我正在使用JTA数据源并定义@TransactionManagement(TransactionManagementType.BEAN)来覆盖事务的控制。

@资源私有事务管理器事务管理器;

返回给我一个NullPointerException当我尝试做一个"transactionManager.begin ();". 有人知道如何解决这个问题吗?

更新:

我使用的代码是:

    @Startup
    @Singleton
    @TransactionManagement(TransactionManagementType.BEAN)
    public class RuntimeContextEJB

{

    @EJB
    private RepositoryRecursosExternosFactoryEJB    repositoryRecursosExternosFactoryEJB;

    @EJB
    private MetodologiaIndiceLiquidezFactoryEJB     metodologiaIndiceLiquidezFactoryEJB;

    @EJB
    private FuncaoMatematicaFactoryEJB              funcaoMatematicaFactoryEJB;

    private boolean                                 bootstrapRunning    = false;

    private List<String>                            dadosMercadoMonitorados;

    @PersistenceContext(unitName = "crv-persistence-unit")
    private EntityManager                           entityManager;

    @Resource
    private TransactionManager transactionManager;


    @PostConstruct
    public void init()
    {
        // comentário
        MotorCalculoContext.setupMotorCalculoContext(repositoryRecursosExternosFactoryEJB, metodologiaIndiceLiquidezFactoryEJB,
                funcaoMatematicaFactoryEJB);
        carregaDadosMercadoMonitorados();

    }


    public void sinalizarInicioBootstrap()
    {
        bootstrapRunning = true;
    }


    public void sinalizarTerminoBootstrap()
    {
        bootstrapRunning = false;
    }


    public boolean isBootstrapRunnnig()
    {
        return bootstrapRunning;
    }

    public void carregaDadosMercadoMonitorados()
    {




        try
        {

            transactionManager.begin();

            this.dadosMercadoMonitorados = (List<String>) entityManager
                    .createQuery(
                            "SELECT DISTINCT(p.parametro.codigoDadoMercado) FROM PlanoExecucaoPasso p WHERE p.parametro.codigoDadoMercado <> '' AND p.parametro.codigoDadoMercado <> '0'")
                    .getResultList();
        }
        catch (Exception e)
        {
        }

    }

}

我认为应该在@Resources注释上添加一个JNDI地址,一个特定于WebSphere的地址,但我真的找不到。

更新:

为什么在容器管理的注入上使用JNDI?由于我从直接注入中获得了一个nullpointer异常,因此尝试使用类似于OReilly Enterprise Java Beans 3.1第6版305页上的ex。

@Resource(mappedName = "java:/TransactionManager")
//mappedName is vendor-specific, and in this case points to an address in JNDI

尝试了这个,但没有成功。

更新

WebSphere没有获得我们的beans注释-真的不知道为什么-因此注释:

@TransactionManagement(TransactionManagementType.BEAN)

没有工作。因此,编辑了de ejb jar。xml并添加了以下代码:

<transaction-type>Bean</transaction-type>

UserTransaction起了作用。谢谢你的回答。

共有3个答案

井浩思
2023-03-14

下面是一些使用UserTransaction来控制事务的示例代码。

@Singleton
@Startup
@TransactionManagement(TransactionManagementType.BEAN) 
public class SampleUT {

Logger logger = Logger.getLogger(SampleUT.class.getName()); 

@Resource
private UserTransaction ut;

@PostConstruct
public void postConstruct()
{
    logger.info("PostConstruct called");

    try {
        ut.begin();
...

您得到的NullPointerException可能与您试图在EJB的构造函数内使用注入的资源有关。您应该知道,在EJB的构造函数完成之前,注入的引用永远不可用,因此如果您尝试在构造函数内使用任何注入的引用,它将抛出NullPointerException。

秋阳荣
2023-03-14

您不需要在编程(BMT)会话bean中使用事务管理器,除非您想在某些情况下挂起()或恢复()相关事务,否则请改用UserTransaction。

但是,您可以通过com获得对websphere中事务管理器的引用。ibm。ws。交易TransactionManagerFactory使用静态方法getTransactionManager()初始化。

public TransactionManager getTransactionManager() {
    return TransactionManagerFactory.getTransactionManager();
}
万俟炯
2023-03-14

当您有bean管理的事务时,您不会使用javax。交易TransactionManager,但您使用的是javax。交易用户事务。

然后调用UserTransaction接口的开始、提交...... etc。

回答更新:

1) 首先,正如我所说,不要使用TransactionManager。使用用户事务

2)因为您想知道UserTransaction对象的JNDI名称。它是java: comp/UserTransaction。但是只有当您的组件不受管理时才需要它。即:Servlet、EJB。该过程称为手动调用JNDI API

3) 提供提交()或回滚()。他们都不在场。

我在看你的课,看起来不错。

那么,问题出在哪里?(可能性)

1) 您的类没有被视为EJB(容器管理),这就是注入失败的原因。

2) 事务服务在EJB@启动之前未启动,或者无法启动。

3) 您在持久性中配置了JTA数据源。xml。在这种情况下,请尝试:

@Resource
private EJBContext context;

userTransaction  = context.getUserTransaction(); 

注意:还请提供完整的堆栈跟踪和persistence.xml,以查明确切的问题。

 类似资料:
  • 问题内容: 下面的代码应在上周五的16:00:00返回。但它返回上周的星期五。如何解决? 更新。我现在使用以下方法-最好的方法吗? Upd2。仅举一个例子。假设今天是 2012年10月5日 。如果当前时间等于或小于 16:00 ,则应返回 2012年9月28日 ,否则返回 2012 年 10月5日 。 问题答案: 与链接的问题一样,您需要使用对象而不是。要获得最终结果,可以使用:

  • 在PHP中通过< code>date('c')很容易获得ISO 8601日期字符串(例如,< code > 2004-02-12t 15:19:21 00:00 ),但是在Objective-C (iPhone)中如何获得它呢?有没有类似的捷径? 这是我发现的很长的路要走: 对于如此核心的东西来说,这似乎是一个非常严格的要求。

  • 问题内容: 如何从SELECT语句的上一个结果行中获取值 如果我们有一个名为cardevent的表,并且有[ID(int),Value(Money)]行,并且其中有一些行,例如 很快… 如何进行一个查询,以获取每个行的ID,值和前一个行值,数据在其中显示如下 很快。 那么,有人可以帮助我获得针对此类问题的最佳解决方案吗? 需要查询帮助 问题答案: 您将不得不将表与自身连接,我不确定这是否是100%

  • 我对GCP和数据流非常熟悉。然而,我想开始测试和部署一些利用GCP上的数据流的流。根据文档和围绕数据流的所有内容,必须使用Apache项目BEAM。因此,根据这里的官方文档,python的受支持版本是2.7 老实说,这是相当失望的,因为Python 2. x版本将消失,因为没有官方支持,每个人都在使用3. x版本。然而,我想知道是否有人知道如何准备梁和GCP数据流在python版本中运行。 我看了

  • 当我登录时,我们可以在Youtube网站顶部看到基于我的Youtube历史记录的个性化推荐视频。现在,我正在尝试使用Youtube数据API v3在Youtube上获取推荐视频。 据我所知,在YouTube API v2中有一个API来获取推荐视频列表,但在v3中被弃用,如下所示: 视频推荐 YouTube数据API (v2)功能:检索视频推荐 v3 API不会检索仅包含为当前API用户推荐的视频