从Tomee服务器上运行的Java应用程序访问Oracle数据库时,出现错误“ ORA-25351:正在使用事务”

时间:2019-05-24 15:00:01

标签: oracle java-ee xa tomee-7

我正在编写一个Web服务方法,该方法先写入第一个模式“ IMMO”,然后再写入另一个模式“ CSF”。 写入第一个架构运行良好,但是第一次尝试写入第二个架构会导致以下错误:

ORA-25351:正在使用的交易

我需要的是一个独特的分布式事务,该事务从Web服务方法的开头开始,到此方法的返回结束。 我的Web服务由无状态EJB实现,该无状态EJB调用其他无状态EJB,所有这些EJB都使用默认事务参数:

  • 未指定事务管理,因此假定为CMT
 
  • 未指定交易属性,因此假定为必需

尽管如此,看来当我尝试与第二个数据源建立连接时,它认为我在另一个会话中。

服务器即将运行7.0.3

我想我在tomee配置中错过了一些东西,但是我什么也找不到...

这是来自tomee.xml的数据源定义:

<Resource id="ImmoDataSource" type="javax.sql.DataSource">
    DataSourceCreator   dbcp
    name            ImmoDataSource
    username        IMMO
    password        ****
    JdbcUrl         jdbc:oracle:thin:@srv-ora5:1521:IBOP
    JdbcDriver      oracle.jdbc.xa.client.OracleXADataSource
    validationQuery     select * from dual
    connectionProperties    useUnicode=false;characterEncoding=WE8MSWIN1252;
    maxTotal        30
    maxIdle         1
    minIdle         0
    maxWaitMillis   60000
    DefaultAutoCommit   false
    testOnBorrow        false
</Resource>

<Resource id="CSFDataSource" type="javax.sql.DataSource">
    DataSourceCreator   dbcp
    name            CSFDataSource
    username        CSF
    password        ***
    JdbcUrl         jdbc:oracle:thin:@srv-ora5:1521:IBOP
    JdbcDriver      oracle.jdbc.xa.client.OracleXADataSource
    validationQuery select * from dual
    connectionProperties    useUnicode=false;characterEncoding=WE8MSWIN1252;
    maxTotal        30
    maxIdle         1
    minIdle         0
    maxWaitMillis   60000
    DefaultAutoCommit   false
    testOnBorrow        false
</Resource>

我希望在第二个架构CSFDataSource中的写入与在第一个架构中的写入相同的事务中执行。

我编写了一个小型Web服务,只有一个小类,它使用相同的tomee.xml,并且重现了问题:

package fr.csf.testxa;

import java.sql.Connection;
import java.sql.SQLException;
import java.sql.Statement;
import javax.annotation.Resource;
import javax.ejb.Stateless;
import javax.jws.WebMethod;
import javax.jws.WebService;
import javax.sql.DataSource;

@Stateless
@WebService
public class TestXa
{
    @Resource
    private DataSource CSFDataSource;

    @Resource
    private DataSource ImmoDataSource;

    @WebMethod
    public String test() throws SQLException
    {
        String ret = "?";

        // This first insert via ImmoDataSource goes well
        Connection cnx = this.ImmoDataSource.getConnection();
        Statement stm = cnx.createStatement();
        stm.executeUpdate( "insert into testxa( id) values ( sys_guid())");

        // The second access gets the ORA-25351 error
        cnx = this.CSFDataSource.getConnection();
        stm = cnx.createStatement();
        stm.executeUpdate( "insert into testxa( id) values ( sys_guid())");

        // We never arrive here because of the SQLException
        ret = "OK";

        return ret;
    }
}

经过几次搜索和多次尝试,我发现只有当两个数据源引用相同的数据库时,才会出现ORA-25351错误。但是我认为引用同一数据库的不同架构并不违法。该代码是很久以前为Weblogic 8.1服务器编写的,并且运行良好。

1 个答案:

答案 0 :(得分:0)

经过很多工作,我发现了一个解释: 我的Oracle JDBC驱动程序版本(ojdbc7.jar)可能与Oracle数据库版本(Oracle 10gR2)不兼容。

这里是Oracle网站的链接: https://docs.oracle.com/en/database/oracle/oracle-database/19/jjdbc/JDBC-getting-started.html#GUID-926E5324-D89A-4A00-B1AE-975C1089F0EA

可以在其中阅读的内容:

Oracle数据库12c第2版(12.2.0.1)JDBC驱动程序已通过受支持的Oracle数据库版本(11.x.0.x)认证。但是,它们没有经过认证可以与较早的不受支持的数据库版本一起使用,例如10.2.x,10.1.x,9.2.x和9.0.1.x。

所以我用一个旧的ojdbc1.4.jar替换了ojdbc7.jar驱动程序。但是现在我 出现其他错误:

无法在事务中登记连接:enlistResource返回'false'。

但是我认为这是另一个问题,我将为此创建另一个问题。

相关问题