2010-07-22 71 views
7

我取消部署使用从Drools规则引擎登录其自己的线程的异步记录器的Java EE应用程序。我使用它来记录规则引擎所做的决定,但我不能让它对吞吐量产生影响,因此它必须在自己的线程中运行。如何在取消部署Java EE应用程序时停止线程?

当我解除表示它没有正确关闭时,我得到异常页面。

while(true){ 
    log(something) 
    sleep(someTime); 
} 

它可能没有时间作出反应时,正确为睡觉和取消部署启动:自记录仪就是这样的一个线程,可能是真实的。不幸的是,我不能从记录器获取线程本身,所以我无法通过@PreDestroy方法加入它。如何取消部署时如何避免异常?

的Excpetions:

[#|2010-07-19T15:50:10.123+0200|WARNING|sun-appserver2.1|javax.enterprise.system.core.classloading|_ThreadID=24;_ThreadName=Thread-258;_RequestID=22a7d379-0813-4248-9095-3fba7f4cb95a;|LDR5206: EJBClassLoader EJBClassLoader : 
doneCalled = true 
doneSnapshot = EJBClassLoader.done() called ON EJBClassLoader : 
urlSet = [URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/jaxp-api-1.3.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/mvel2-2.0.10.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/activation-1.1.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/stax-1.2.0.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/jms-1.1.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/commons-lang-2.4.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/joda-time-1.6.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/drools-compiler-5.0.1.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/commons-email-1.2.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/commons-beanutils-core-1.8.0.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/Mailforwarder-pojo-1.0.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/xml-apis-1.0.b2.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/commons-logging-1.1.1.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/janino-2.5.15.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/commons-digester-1.8.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/drools-api-5.0.1.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/commons-net-2.0.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/commons-lang-2.5.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/core-3.4.2.v_883_R34x.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/xpp3_min-1.1.4c.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/stax-api-1.0.1.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/commons-configuration-1.6.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/commons-collections-3.2.1.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/xstream-1.3.1.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/commons-beanutils-1.7.0.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/core-pojo-1.0.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/core-common-1.0.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/xml-writer-0.2.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/antlr-runtime-3.1.1.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/mail-1.4.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/activation.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/lib/drools-core-5.0.1.jar, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/applications/j2ee-apps/mailforwarder/Mailforwarder-ejbjar-1.0_jar/, URLEntry : file:/home/arne/env/runtime/glassfish/domains/domain1/generated/ejb/j2ee-apps/mailforwarder/] 
doneCalled = false 
Parent -> EJBClassLoader : 
urlSet = [] 
doneCalled = false 
Parent -> [email protected] 


AT Mon Jul 19 15:47:21 CEST 2010 
BY :com.sun.enterprise.loader.EJBClassLoader.printStackTraceToString(EJBClassLoader.java:813) 
com.sun.enterprise.loader.EJBClassLoader.done(EJBClassLoader.java:173) 
com.sun.enterprise.server.AbstractLoader.done(AbstractLoader.java:355) 
com.sun.enterprise.server.ApplicationLoader.unload(ApplicationLoader.java:268) 
com.sun.enterprise.server.TomcatApplicationLoader.unload(TomcatApplicationLoader.java:218) 
com.sun.enterprise.server.ExtendedApplicationLoader.unload(ExtendedApplicationLoader.java:263) 
com.sun.enterprise.server.ApplicationManager.applicationUndeployed(ApplicationManager.java:525) 
com.sun.enterprise.server.ApplicationManager.applicationUndeployed(ApplicationManager.java:703) 
com.sun.enterprise.admin.event.AdminEventMulticaster.invokeApplicationDeployEventListener(AdminEventMulticaster.java:961) 
com.sun.enterprise.admin.event.AdminEventMulticaster.handleApplicationDeployEvent(AdminEventMulticaster.java:943) 
com.sun.enterprise.admin.event.AdminEventMulticaster.processEvent(AdminEventMulticaster.java:467) 
com.sun.enterprise.admin.event.AdminEventMulticaster.multicastEvent(AdminEventMulticaster.java:182) 
com.sun.enterprise.admin.server.core.DeploymentNotificationHelper.multicastEvent(DeploymentNotificationHelper.java:308) 
com.sun.enterprise.deployment.phasing.DeploymentServiceUtils.multicastEvent(DeploymentServiceUtils.java:231) 
com.sun.enterprise.deployment.phasing.ServerDeploymentTarget.sendStopEvent(ServerDeploymentTarget.java:332) 
com.sun.enterprise.deployment.phasing.ApplicationStopPhase.runPhase(ApplicationStopPhase.java:136) 
com.sun.enterprise.deployment.phasing.DeploymentPhase.executePhase(DeploymentPhase.java:108) 
com.sun.enterprise.deployment.phasing.PEDeploymentService.executePhases(PEDeploymentService.java:966) 
com.sun.enterprise.deployment.phasing.PEDeploymentService.undeploy(PEDeploymentService.java:333) 
com.sun.enterprise.deployment.phasing.PEDeploymentService.undeploy(PEDeploymentService.java:308) 
com.sun.enterprise.admin.mbeans.ApplicationsConfigMBean.undeploy(ApplicationsConfigMBean.java:667) 
sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) 
sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39) 
sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25) 
java.lang.reflect.Method.invoke(Method.java:597) 
com.sun.enterprise.admin.MBeanHelper.invokeOperationInBean(MBeanHelper.java:390) 
com.sun.enterprise.admin.MBeanHelper.invokeOperationInBean(MBeanHelper.java:373) 
com.sun.enterprise.admin.config.BaseConfigMBean.invoke(BaseConfigMBean.java:477) 
com.sun.jmx.interceptor.DefaultMBeanServerInterceptor.invoke(DefaultMBeanServerInterceptor.java:836) 
com.sun.jmx.mbeanserver.JmxMBeanServer.invoke(JmxMBeanServer.java:761) 
sun.reflect.GeneratedMethodAccessor13.invoke(Unknown Source) 
sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25) 
java.lang.reflect.Method.invoke(Method.java:597) 
com.sun.enterprise.admin.util.proxy.ProxyClass.invoke(ProxyClass.java:90) 
$Proxy1.invoke(Unknown Source) 
com.sun.enterprise.admin.server.core.jmx.SunoneInterceptor.invoke(SunoneInterceptor.java:304) 
com.sun.enterprise.interceptor.DynamicInterceptor.invoke(DynamicInterceptor.java:170) 
com.sun.enterprise.deployment.autodeploy.AutoDeployer.invokeUndeploymentService(AutoDeployer.java:903) 
com.sun.enterprise.deployment.autodeploy.AutoDeployer.undeployJavaEEArchive(AutoDeployer.java:399) 
com.sun.enterprise.deployment.autodeploy.AutoDeployer.undeployApplication(AutoDeployer.java:381) 
com.sun.enterprise.deployment.autodeploy.AutoDeployer.undeployAll(AutoDeployer.java:315) 
com.sun.enterprise.deployment.autodeploy.AutoDeployControllerImpl$AutoDeployTask.run(AutoDeployControllerImpl.java:375) 
java.util.TimerThread.mainLoop(Timer.java:512) 
java.util.TimerThread.run(Timer.java:462) 
Parent -> EJBClassLoader : 
urlSet = [] 
doneCalled = false 
Parent -> [email protected] 

was requested to find resource META-INF/services/javax.xml.datatype.DatatypeFactory after done was invoked from the following stack trace 
java.lang.Throwable 
     at com.sun.enterprise.loader.EJBClassLoader.findResource(EJBClassLoader.java:459) 
     at java.lang.ClassLoader.getResource(ClassLoader.java:978) 
     at java.lang.ClassLoader.getResourceAsStream(ClassLoader.java:1168) 
     at com.sun.enterprise.loader.EJBClassLoader.getResourceAsStream(EJBClassLoader.java:796) 
     at javax.xml.datatype.SecuritySupport$4.run(SecuritySupport.java:92) 
     at java.security.AccessController.doPrivileged(Native Method) 
     at javax.xml.datatype.SecuritySupport.getResourceAsStream(SecuritySupport.java:85) 
     at javax.xml.datatype.FactoryFinder.findJarServiceProvider(FactoryFinder.java:250) 
     at javax.xml.datatype.FactoryFinder.find(FactoryFinder.java:223) 
     at javax.xml.datatype.DatatypeFactory.newInstance(DatatypeFactory.java:131) 
     at com.thoughtworks.xstream.converters.extended.DurationConverter.<init>(DurationConverter.java:33) 
     at sun.reflect.GeneratedConstructorAccessor70.newInstance(Unknown Source) 
     at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:27) 
     at java.lang.reflect.Constructor.newInstance(Constructor.java:513) 
     at com.thoughtworks.xstream.XStream.dynamicallyRegisterConverter(XStream.java:725) 
     at com.thoughtworks.xstream.XStream.setupConverters(XStream.java:696) 
     at com.thoughtworks.xstream.XStream.<init>(XStream.java:445) 
     at com.thoughtworks.xstream.XStream.<init>(XStream.java:385) 
     at com.thoughtworks.xstream.XStream.<init>(XStream.java:323) 
     at org.drools.audit.WorkingMemoryFileLogger.writeToDisk(WorkingMemoryFileLogger.java:120) 
     at org.drools.audit.ThreadedWorkingMemoryFileLogger.writeToDisk(ThreadedWorkingMemoryFileLogger.java:38) 
     at org.drools.audit.ThreadedWorkingMemoryFileLogger$Writer.run(ThreadedWorkingMemoryFileLogger.java:50) 
     at java.lang.Thread.run(Thread.java:619) 
|#] 

我在这个问题上,遗憾对于想我没有做足够清晰。我问了一个新的question here

回答

12

而不是使用ScheduledExecutorService#scheduleAtFixedRate()而不是老式的Thread#sleep()。您可以使用ServletContextListener在webapp的启动时运行它,并在webapp关闭时停止它。

@WebListener 
public class Config implements ServletContextListener { 

    private ScheduledExecutorService scheduler; 

    @Override 
    public void contextInitialized(ServletContextEvent event) { 
     scheduler = Executors.newSingleThreadScheduledExecutor(); 
     scheduler.scheduleAtFixedRate(new Task(), 0, 1, TimeUnit.MINUTES); // Schedule to run every minute. 
    } 

    @Override 
    public void contextDestroyed(ServletContextEvent event) { 
     scheduler.shutdown(); // Important! This stops the thread. 
    } 

} 

哪里Task可以是这样的:

public class Task implements Runnable { 

    @Override 
    public void run() { 
     log(something); 
    } 

} 

如果您的环境不支持Servlet 3.0 @WebListener,然后将其注册为web.xml如下让它运行:

<listener> 
    <listener-class>com.example.Config</listener-class> 
</listener> 
+0

感谢您的回答。我没有自己实现记录器,它带有Drools规则引擎。所以我不能改变实现。我也无法获得它用于执行日志记录的线程。这没有吸气。我只是研究了drools类的源代码,并看到了使用sleep函数的实现。所以我的问题依然存在:有什么方法可以知道应用何时解除部署? finallize来得太晚,@PreDestroy在容器正常操作期间被调用。应用程序如何知道它何时未被部署? – Arne 2010-07-23 07:37:30

+0

澄清:异常说:“输入流已被确定或强制关闭,没有明确关闭”。我的问题是:我如何取消部署时关闭它?关闭是用close()方法完成的,但是什么时候? – Arne 2010-07-23 07:49:51

相关问题