早上好。我需要实现一个应用程序,每x分钟启动n个任务,每个任务写入MySQL表。我以为我会用以下方法修复它:
这是我的解决方案。以下类是Timer EJB:
@Singleton
public class MyTimerService {
@EJB
private WorkerPool worker;
@Schedule(second="*", minute="*/3",hour="*", persistent=false)
public void doWork(){
worker.execute();
}
}
这是Executor的实现:
public class ThreadExecutor implements Executor{
@Asynchronous
@Override
public void execute(Runnable command) {
ExecutorService executor = Executors.newFixedThreadPool(5);
executor.execute(command);
}
}
并完成,Class运行Thread:
@Stateless
public class WorkerPool {
@EJB
private Executor executor;
@EJB(name = "Dao")
private IDao dao;
public void execute() {
try {
List<Object> info = dao.readTable();
if (info.size() > 0) {
for (int i = 0; i < info.size(); i++) {
Object temp = info.get(i);
Runnable worker = new WorkerThread(temp, dao);
executor.execute(worker);
}
Thread.sleep(30000);
}
} catch (Throwable e) {
e.printStackTrace();
}
}
我部署了我的应用程序服务器Glassfish。这是错误:
[2015-07-28T17:06:53.995+0200] [glassfish 4.1] [WARNING] [AS-EJB-00056] [javax.enterprise.ejb.container] [tid: _ThreadID=186 _ThreadName=__ejb-thread-pool12] [timeMillis: 1438096013995] [levelValue: 900] [[
A system exception occurred during an invocation on EJB BetFinderTimerService, method: public void com.surebetfinder.timer.BetFinderTimerService.doWork()]]
[2015-07-28T17:06:53.996+0200] [glassfish 4.1] [WARNING] [] [javax.enterprise.ejb.container] [tid: _ThreadID=186 _ThreadName=__ejb-thread-pool12] [timeMillis: 1438096013996] [levelValue: 900] [[
javax.ejb.EJBException: javax.ejb.EJBException: javax.ejb.CreateException: Could not create stateless EJB
at com.sun.ejb.containers.StatelessSessionContainer._getContext(StatelessSessionContainer.java:435)
at com.sun.ejb.containers.BaseContainer.getContext(BaseContainer.java:2579)
at com.sun.ejb.containers.BaseContainer.preInvoke(BaseContainer.java:1971)
at com.sun.ejb.containers.EJBLocalObjectInvocationHandler.invoke(EJBLocalObjectInvocationHandler.java:210)
at com.sun.ejb.containers.EJBLocalObjectInvocationHandlerDelegate.invoke(EJBLocalObjectInvocationHandlerDelegate.java:88)
at com.sun.proxy.$Proxy296.execute(Unknown Source)
at com.surebetfinder.logic.processi.__EJB31_Generated__WorkerPool__Intf____Bean__.execute(Unknown Source)
at com.surebetfinder.timer.BetFinderTimerService.doWork(BetFinderTimerService.java:19)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:497)
at org.glassfish.ejb.security.application.EJBSecurityManager.runMethod(EJBSecurityManager.java:1081)
at org.glassfish.ejb.security.application.EJBSecurityManager.invoke(EJBSecurityManager.java:1153)
at com.sun.ejb.containers.BaseContainer.invokeBeanMethod(BaseContainer.java:4786)
at com.sun.ejb.EjbInvocation.invokeBeanMethod(EjbInvocation.java:656)
at com.sun.ejb.containers.interceptors.AroundInvokeChainImpl.invokeNext(InterceptorManager.java:822)
at com.sun.ejb.EjbInvocation.proceed(EjbInvocation.java:608)
at org.jboss.weld.ejb.AbstractEJBRequestScopeActivationInterceptor.aroundInvoke(AbstractEJBRequestScopeActivationInterceptor.java:55)
at org.jboss.weld.ejb.SessionBeanInterceptor.aroundInvoke(SessionBeanInterceptor.java:52)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:497)
at com.sun.ejb.containers.interceptors.AroundInvokeInterceptor.intercept(InterceptorManager.java:883)
at com.sun.ejb.containers.interceptors.AroundInvokeChainImpl.invokeNext(InterceptorManager.java:822)
at com.sun.ejb.EjbInvocation.proceed(EjbInvocation.java:608)
at com.sun.ejb.containers.interceptors.SystemInterceptorProxy.doCall(SystemInterceptorProxy.java:163)
at com.sun.ejb.containers.interceptors.SystemInterceptorProxy.aroundTimeout(SystemInterceptorProxy.java:145)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:497)
at com.sun.ejb.containers.interceptors.AroundInvokeInterceptor.intercept(InterceptorManager.java:883)
at com.sun.ejb.containers.interceptors.AroundInvokeChainImpl.invokeNext(InterceptorManager.java:822)
at com.sun.ejb.containers.interceptors.InterceptorManager.intercept(InterceptorManager.java:369)
at com.sun.ejb.containers.BaseContainer.__intercept(BaseContainer.java:4758)
at com.sun.ejb.containers.BaseContainer.intercept(BaseContainer.java:4746)
at com.sun.ejb.containers.BaseContainer.callEJBTimeout(BaseContainer.java:4051)
at com.sun.ejb.containers.EJBTimerService.deliverTimeout(EJBTimerService.java:1199)
at com.sun.ejb.containers.EJBTimerService.access$000(EJBTimerService.java:89)
at com.sun.ejb.containers.EJBTimerService$TaskExpiredWork.run(EJBTimerService.java:1919)
at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511)
at java.util.concurrent.FutureTask.run(FutureTask.java:266)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
at java.lang.Thread.run(Thread.java:745)
Caused by: javax.ejb.EJBException: javax.ejb.CreateException: Could not create stateless EJB
at com.sun.ejb.containers.StatelessSessionContainer$SessionContextFactory.create(StatelessSessionContainer.java:700)
at com.sun.ejb.containers.util.pool.NonBlockingPool.getObject(NonBlockingPool.java:246)
at com.sun.ejb.containers.StatelessSessionContainer._getContext(StatelessSessionContainer.java:430)
... 46 more
Caused by: javax.ejb.CreateException: Could not create stateless EJB
at com.sun.ejb.containers.StatelessSessionContainer.createStatelessEJB(StatelessSessionContainer.java:514)
at com.sun.ejb.containers.StatelessSessionContainer.access$000(StatelessSessionContainer.java:97)
at com.sun.ejb.containers.StatelessSessionContainer$SessionContextFactory.create(StatelessSessionContainer.java:698)
... 48 more
Caused by: java.lang.IllegalStateException: Exception attempting to inject Remote ejb-ref name=com.surebetfinder.logic.processi.WorkerPool/executor,Remote 3.x interface =java.util.concurrent.Executor,ejb-link=null,lookup=,mappedName=,jndi-name=java.util.concurrent.Executor,refType=Session into class com.surebetfinder.logic.processi.WorkerPool: Lookup failed for 'java:comp/env/com.surebetfinder.logic.processi.WorkerPool/executor' in SerialContext[myEnv={java.naming.factory.initial=com.sun.enterprise.naming.impl.SerialInitContextFactory, java.naming.factory.state=com.sun.corba.ee.impl.presentation.rmi.JNDIStateFactoryImpl, java.naming.factory.url.pkgs=com.sun.enterprise.naming}
at org.glassfish.weld.services.InjectionServicesImpl.aroundInject(InjectionServicesImpl.java:175)
at org.jboss.weld.injection.InjectionContextImpl.run(InjectionContextImpl.java:46)
at org.jboss.weld.injection.producer.DefaultInjector.inject(DefaultInjector.java:68)
at org.jboss.weld.injection.producer.StatelessSessionBeanInjector.inject(StatelessSessionBeanInjector.java:58)
at org.jboss.weld.injection.producer.ejb.SessionBeanInjectionTarget.inject(SessionBeanInjectionTarget.java:117)
at org.glassfish.weld.services.JCDIServiceImpl.injectEJBInstance(JCDIServiceImpl.java:257)
at com.sun.ejb.containers.BaseContainer.injectEjbInstance(BaseContainer.java:1748)
at com.sun.ejb.containers.StatelessSessionContainer.createStatelessEJB(StatelessSessionContainer.java:475)
... 50 more
Caused by: com.sun.enterprise.container.common.spi.util.InjectionException: Exception attempting to inject Remote ejb-ref name=com.surebetfinder.logic.processi.WorkerPool/executor,Remote 3.x interface =java.util.concurrent.Executor,ejb-link=null,lookup=,mappedName=,jndi-name=java.util.concurrent.Executor,refType=Session into class com.surebetfinder.logic.processi.WorkerPool: Lookup failed for 'java:comp/env/com.surebetfinder.logic.processi.WorkerPool/executor' in SerialContext[myEnv={java.naming.factory.initial=com.sun.enterprise.naming.impl.SerialInitContextFactory, java.naming.factory.state=com.sun.corba.ee.impl.presentation.rmi.JNDIStateFactoryImpl, java.naming.factory.url.pkgs=com.sun.enterprise.naming}
at com.sun.enterprise.container.common.impl.util.InjectionManagerImpl._inject(InjectionManagerImpl.java:740)
at com.sun.enterprise.container.common.impl.util.InjectionManagerImpl.inject(InjectionManagerImpl.java:507)
at com.sun.enterprise.container.common.impl.util.InjectionManagerImpl.injectInstance(InjectionManagerImpl.java:170)
at org.glassfish.weld.services.InjectionServicesImpl.aroundInject(InjectionServicesImpl.java:165)
... 57 more
Caused by: javax.naming.NamingException: Lookup failed for 'java:comp/env/com.surebetfinder.logic.processi.WorkerPool/executor' in SerialContext[myEnv={java.naming.factory.initial=com.sun.enterprise.naming.impl.SerialInitContextFactory, java.naming.factory.state=com.sun.corba.ee.impl.presentation.rmi.JNDIStateFactoryImpl, java.naming.factory.url.pkgs=com.sun.enterprise.naming} [Root exception is javax.naming.NamingException: Exception resolving Ejb for 'Remote ejb-ref name=com.surebetfinder.logic.processi.WorkerPool/executor,Remote 3.x interface =java.util.concurrent.Executor,ejb-link=null,lookup=,mappedName=,jndi-name=java.util.concurrent.Executor,refType=Session' . Actual (possibly internal) Remote JNDI name used for lookup is 'java.util.concurrent.Executor#java.util.concurrent.Executor' [Root exception is javax.naming.NamingException: Lookup failed for 'java.util.concurrent.Executor#java.util.concurrent.Executor' in SerialContext[myEnv={java.naming.factory.initial=com.sun.enterprise.naming.impl.SerialInitContextFactory, java.naming.factory.state=com.sun.corba.ee.impl.presentation.rmi.JNDIStateFactoryImpl, java.naming.factory.url.pkgs=com.sun.enterprise.naming} [Root exception is javax.naming.NameNotFoundException: java.util.concurrent.Executor#java.util.concurrent.Executor not found]]]
at com.sun.enterprise.naming.impl.SerialContext.lookup(SerialContext.java:491)
at com.sun.enterprise.naming.impl.SerialContext.lookup(SerialContext.java:438)
at javax.naming.InitialContext.lookup(InitialContext.java:417)
at javax.naming.InitialContext.lookup(InitialContext.java:417)
at com.sun.enterprise.container.common.impl.util.InjectionManagerImpl._inject(InjectionManagerImpl.java:636)
... 60 more
Caused by: javax.naming.NamingException: Exception resolving Ejb for 'Remote ejb-ref name=com.surebetfinder.logic.processi.WorkerPool/executor,Remote 3.x interface =java.util.concurrent.Executor,ejb-link=null,lookup=,mappedName=,jndi-name=java.util.concurrent.Executor,refType=Session' . Actual (possibly internal) Remote JNDI name used for lookup is 'java.util.concurrent.Executor#java.util.concurrent.Executor' [Root exception is javax.naming.NamingException: Lookup failed for 'java.util.concurrent.Executor#java.util.concurrent.Executor' in SerialContext[myEnv={java.naming.factory.initial=com.sun.enterprise.naming.impl.SerialInitContextFactory, java.naming.factory.state=com.sun.corba.ee.impl.presentation.rmi.JNDIStateFactoryImpl, java.naming.factory.url.pkgs=com.sun.enterprise.naming} [Root exception is javax.naming.NameNotFoundException: java.util.concurrent.Executor#java.util.concurrent.Executor not found]]
at com.sun.ejb.EjbNamingReferenceManagerImpl.resolveEjbReference(EjbNamingReferenceManagerImpl.java:188)
at com.sun.enterprise.container.common.impl.ComponentEnvManagerImpl$EjbReferenceProxy.create(ComponentEnvManagerImpl.java:1015)
at com.sun.enterprise.naming.impl.GlassfishNamingManagerImpl.lookup(GlassfishNamingManagerImpl.java:745)
at com.sun.enterprise.naming.impl.GlassfishNamingManagerImpl.lookup(GlassfishNamingManagerImpl.java:715)
at com.sun.enterprise.naming.impl.JavaURLContext.lookup(JavaURLContext.java:159)
at com.sun.enterprise.naming.impl.SerialContext.lookup(SerialContext.java:471)
... 64 more
Caused by: javax.naming.NamingException: Lookup failed for 'java.util.concurrent.Executor#java.util.concurrent.Executor' in SerialContext[myEnv={java.naming.factory.initial=com.sun.enterprise.naming.impl.SerialInitContextFactory, java.naming.factory.state=com.sun.corba.ee.impl.presentation.rmi.JNDIStateFactoryImpl, java.naming.factory.url.pkgs=com.sun.enterprise.naming} [Root exception is javax.naming.NameNotFoundException: java.util.concurrent.Executor#java.util.concurrent.Executor not found]
at com.sun.enterprise.naming.impl.SerialContext.lookup(SerialContext.java:491)
at com.sun.enterprise.naming.impl.SerialContext.lookup(SerialContext.java:438)
at javax.naming.InitialContext.lookup(InitialContext.java:417)
at javax.naming.InitialContext.lookup(InitialContext.java:417)
at com.sun.ejb.EjbNamingReferenceManagerImpl.resolveEjbReference(EjbNamingReferenceManagerImpl.java:183)
... 69 more
Caused by: javax.naming.NameNotFoundException: java.util.concurrent.Executor#java.util.concurrent.Executor not found
at com.sun.enterprise.naming.impl.TransientContext.doLookup(TransientContext.java:237)
at com.sun.enterprise.naming.impl.TransientContext.lookup(TransientContext.java:204)
at com.sun.enterprise.naming.impl.SerialContextProviderImpl.lookup(SerialContextProviderImpl.java:66)
at com.sun.enterprise.naming.impl.LocalSerialContextProviderImpl.lookup(LocalSerialContextProviderImpl.java:114)
at com.sun.enterprise.naming.impl.SerialContext.lookup(SerialContext.java:478)
... 73 more
]]
我哪里错了?
答案 0 :(得分:0)
正如加布里埃尔所说,当你写作
@EJB
private Executor executor;
您告诉容器,而Executor
是EJB本地或远程接口,容器无法在JNDI中查看此接口。
试试这个:
@EJB
private ThreadExecutor executor;
请求&#34; no interface&#34;而不是豆的视图。或者,您可以编写自己的ThreadExecutor
接口。
(旁白:严格来说,这种行为受EJB 3.1规范第4.9.7-4.9.8节的约束,我不认为你违反了它规定的任何规则,所以这可能是Glassfish的错误行为?)
那就是说,我认为你的ThreadExecutor
实现异步创建了一个线程池,然后旋转一个线程来执行工作,我认为这是多余的。为什么不使用WorkerThread
方法将@Asynchronous
转换为EJB?