Jboss 应用程序中EJB连接保持打开,后续连接保持打开和关闭的问题

Jboss 应用程序中EJB连接保持打开,后续连接保持打开和关闭的问题,jboss,ejb,Jboss,Ejb,在打开和关闭其他ejb连接时保持和ejb连接处于打开状态是常见的还是可以接受的?还是应该在客户端完成连接并为后续任务打开新连接后立即关闭连接 我目前正在开发一个使用EJB的Swing应用程序(JBossAS 7.1.1.final)。应用程序打开一个ejb连接(即创建一个InitialContext实例),然后在应用程序保持运行的情况下,将该InitialContext用于常见任务。在许多长时间运行的操作中,会创建额外的ejb连接(和InitialContext)。此连接用于单个长时间运行的进程

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

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

在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);
        }
    }

}
package com.myCompany.myApp.examples.errors.ejb;
导入java.util.List;
导入java.util.Properties;
导入javax.naming.Context;
导入javax.naming.InitialContext;
导入org.apache.log4j.Logger;
导入org.junit.Test;
导入com.myCompany.myApp.client.jboss.JBossEJBClient;
导入com.myCompany.myApp.dao.client.myAppServiceClient;
导入com.myCompany.myApp.dao.client.myAppServiceClientParams;
导入com.myCompany.myApp.testing.util.logging.LoggerForIntegrationTests;
导入com.myCompany.myAppserver.dao.remote.AuthorityDao;
导入com.myCompany.myAppserver.types.TAuthority;
导入com.myCompany.install.util.ejb.ejbclient.myAppServiceClientFactory;
公共类EjbConnectionNotClosedErrorExample{
私有静态记录器Logger=LoggerForIntegrationTests.get();
私有静态最终整数计数=100;
@试验
public void两个案例都应该成功(){
试一试{
debug(“执行有效的案例”);
多斯特(真);
debug(“使用有效的案例完成”);
logger.debug(“\n\n\n”);
logger.debug(“****************************正在执行失败的案例****************************”);
doTest(假);
debug(“使用不起作用的用例完成”);
}捕获(异常扩展){
exp.printStackTrace();
抛出新的运行时异常(exp);
}
}
私有void点测试(布尔闭合连接){
myAppServiceClientParams params=myAppServiceClientFactory.getDefaultClientParams();
JBossEJBClient blocker=新JBossEJBClient();
阻塞器。初始化(参数);
if(closeConnection==true){
blocker.close();
}
int max=计数;
对于(int i=0;i

这是JBoss AS 7.1.1.final特有的错误吗?

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

我见过防火墙在一段时间后像这样断开连接。它可能有几个问题:1#连接:连接断开2#安全:用户/传递无效3#EJB丢失:已连接,但是ejb不存在4#SSL JBoss保持与另一台服务器的持久连接,因此当客户端看到此消息时,意味着没有与具有您试图调用的ejb的服务器的连接,因此,当连接到另一台服务器失败时,将记录一条消息。@SteveC:我认为这不是这里发生的事情,因为JUnit测试将在大约一秒钟内执行。@AnupDey:这可能不是您列出的任何因素,因为在连接失败之前,我成功连接到实例超过100次。Che