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

EJB连接保持打开状态并打开和关闭后续连接的应用程序问题

田镜
2023-03-14

在打开和关闭其他ejb连接时保持和ejb连接打开是常见的还是可以接受的,还是应该在客户端完成连接并为后续任务打开新连接后立即关闭连接?

我目前正在开发一个使用EJB(JBoss AS7.1.1.final)的Swing应用程序。该应用程序打开一个ejb连接(即创建一个SynalContext实例),然后在应用程序保持运行的情况下将该SynalContext用于常见任务。有许多长时间运行的操作,其中创建了一个额外的ejb连接(和SynalContext)。此连接用于单个长时间运行的进程,然后关闭。

在JBoss上,大约在第40个连接打开和关闭后,我得到如下所示的异常。

2017 May 15, 16:29:03 INFO  - (JBossEJBClient.java:121) initialize - JNDI context initialized. 
java.lang.IllegalStateException: No EJB receiver available for handling [appName:dtsjboss,modulename:dtsserverejb,distinctname:] combination for invocation context org.jboss.ejb.client.EJBClientInvocationContext@4e692639
    at org.jboss.ejb.client.EJBClientContext.requireEJBReceiver(EJBClientContext.java:584)
    at org.jboss.ejb.client.ReceiverInterceptor.handleInvocation(ReceiverInterceptor.java:119)
    at org.jboss.ejb.client.EJBClientInvocationContext.sendRequest(EJBClientInvocationContext.java:181)
    at org.jboss.ejb.client.EJBInvocationHandler.doInvoke(EJBInvocationHandler.java:136)
    at org.jboss.ejb.client.EJBInvocationHandler.doInvoke(EJBInvocationHandler.java:121)
    at org.jboss.ejb.client.EJBInvocationHandler.invoke(EJBInvocationHandler.java:104)
    at com.sun.proxy.$Proxy4.getAuthorities(Unknown Source)
    at com.apelon.dts.examples.errors.ejb.EjbConnectionNotClosedErrorExample.doTest(EjbConnectionNotClosedErrorExample.java:53)
    at com.apelon.dts.examples.errors.ejb.EjbConnectionNotClosedErrorExample.bothCasesShouldSucceed(EjbConnectionNotClosedErrorExample.java:34)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:606)
    at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:44)
    at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:15)
    at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:41)
    at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:20)
    at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:76)
    at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:50)
    at org.junit.runners.ParentRunner$3.run(ParentRunner.java:193)
    at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:52)
    at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:191)
    at org.junit.runners.ParentRunner.access$000(ParentRunner.java:42)
    at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:184)
    at org.junit.runners.ParentRunner.run(ParentRunner.java:236)
    at org.eclipse.jdt.internal.junit4.runner.JUnit4TestReference.run(JUnit4TestReference.java:50)
    at org.eclipse.jdt.internal.junit.runner.TestExecution.run(TestExecution.java:38)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:467)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:683)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run(RemoteTestRunner.java:390)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main(RemoteTestRunner.java:197)

如果我运行下面的代码,则使用并关闭ejb连接的情况可以正常工作,但单个连接保持打开的情况会因上述堆栈跟踪而失败。

package com.myCompany.myApp.examples.errors.ejb;

import java.util.List;
import java.util.Properties;

import javax.naming.Context;
import javax.naming.InitialContext;

import org.apache.log4j.Logger;
import org.junit.Test;

import com.myCompany.myApp.client.jboss.JBossEJBClient;
import com.myCompany.myApp.dao.client.myAppServiceClient;
import com.myCompany.myApp.dao.client.myAppServiceClientParams;
import com.myCompany.myApp.testing.util.logging.LoggerForIntegrationTests;
import com.myCompany.myAppserver.dao.remote.AuthorityDao;
import com.myCompany.myAppserver.types.TAuthority;
import com.myCompany.install.util.ejb.ejbclient.myAppServiceClientFactory;

public class EjbConnectionNotClosedErrorExample {

    private static Logger logger = LoggerForIntegrationTests.get();

    private static final int COUNT = 100;

    @Test
    public void bothCasesShouldSucceed() {
        try {
            logger.debug("Doing case that works");
            doTest(true);
            logger.debug("Done with case that works.");
            logger.debug("\n\n\n");
            logger.debug("********************* DOING CASE THAT FAILS *********************");
            doTest(false);
            logger.debug("Done with use case that didn't work.");
        } catch (Exception exp) {
            exp.printStackTrace();
            throw new RuntimeException(exp);
        }
    }

    private void doTest(boolean closeConnection) {
        myAppServiceClientParams params = myAppServiceClientFactory.getDefaultClientParams();
        JBossEJBClient blocker = new JBossEJBClient();
        blocker.initialize(params);
        if (closeConnection == true) {
            blocker.close();
        }
        int max = COUNT;
        for (int i = 0; i < max; i++) {
            myAppServiceClient client = myAppServiceClientFactory.getDefaultClient();
            AuthorityDao dao = client.createAuthorityDao();
            List<TAuthority> list = dao.getAuthorities();
            logger.debug("CONNECTION " + (i + 1) + " ------------------------------------------------");
            logger.debug("Got " + list.size() + " authorities.");
            client.close();
        }
        System.out.println("");
    }

    public void initialize(myAppServiceClientParams params) {
        this.initialize(params.getHost(), params.getPort(), params.getInstance(), params.getUid(), params.getPwd());
    }

    public void initialize(String host, int port, String instance, String user, String password) {
        final Properties jndiProperties = new Properties();
        String providerURL = "remote://" + host + ":" + port;
        jndiProperties.put(Context.INITIAL_CONTEXT_FACTORY, org.jboss.naming.remote.client.InitialContextFactory.class.getName());
        jndiProperties.put(Context.PROVIDER_URL, providerURL);
        jndiProperties.put("jboss.naming.client.ejb.context", true);
        jndiProperties.put("jboss.naming.client.connect.options.org.xnio.Options.SASL_POLICY_NOPLAINTEXT", "false");
        // Explicitly specify STARTTLS = false for connecting to Wildfly v10
        jndiProperties.put("jboss.naming.client.connect.options.org.xnio.Options.SSL_STARTTLS", "false");
        jndiProperties.put(Context.SECURITY_PRINCIPAL, user);
        jndiProperties.put(Context.SECURITY_CREDENTIALS, password);
        try {
            InitialContext ctx = new InitialContext(jndiProperties);
            ctx.getEnvironment();
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
    }

}

这是JBoss AS 7.1.1特有的bug吗。最终的

共有1个答案

双恩
2023-03-14

这里的问题是,一个连接保持打开状态,并被应用程序的主线程用作资源,这(出于某种原因)导致JBoss无法完全取消分配其他连接。解决方案是在打开该连接时获取对该连接的引用,然后在创建任何其他新连接之前关闭该连接,然后在创建新连接后立即重新打开主线程使用的连接。

 类似资料:
  • 问题内容: 在许多使用MongoDB的入门示例中,您将看到类似以下的代码: 如果MongoDB与任何其他数据库系统一样,并且操作通常在时间上很昂贵。 所以,我的问题是这样的:只需执行一次,将返回值分配给某个全局模块即可,模块中具有各种功能就可以进行各种与数据库相关的工作(将文档插入集合,更新文档等)。 ),然后由应用程序的其他部分调用它们(从而重新使用该值),然后,在应用程序完成后,才执行。 换句

  • 问题内容: 我正在通过com端口连续接收数据并进行一些解码。解码完成后,我必须将结果存储在sql数据库中。我在想,因为解码是每秒完成数十次(在while循环中始终运行),并且如果明智的做法是打开和关闭与sql server的连接,则每秒需要将数据存储到数据库数十次。每个while循环或只是使其保持打开状态并继续将数据写入数据库。首先这可能吗?其次,如果连接保持打开状态,那么第三方应用程序或计算机可

  • 我遇到了这个问题:对于Vaadin7,我已经配置了我的持久性。xml,下面是代码 http://java.sun.com/xml/ns/persistence/persistence_2_0.xsd“version=“2.0” 当我创建一个新的JPA容器并将其绑定到一个表时,我会在MSSQL活动监视器上看到我的新连接,但如果会话超时或注销,我仍然会在SQL上看到连接。 如果我在应用程序中重新登录,

  • 问题内容: 我有一个bukkit插件(minecraft),需要连接到数据库。 数据库连接应该一直保持打开状态,还是在需要时打开和关闭? 问题答案: 数据库连接仅在需要时才打开,并在完成所有必要的工作后关闭。代码示例: 在Java 7之前: try { con = … //retrieve the database connection //do your work… } catch (SQLEx

  • 我有一个bukkit插件(minecraft),需要连接到数据库。 数据库连接应该一直保持打开状态,还是在需要时打开和关闭?

  • 在Python中,我将“WebSockets”库用于websocket客户端。 问题是一旦收到响应,客户端websocket连接就会断开。我希望连接保持打开,以便以后可以发送和接收消息。 为了保持websocket打开并能够在以后发送和接收消息,我需要做哪些更改?