Servlet初始化多次



我们正在部署一个IIS站点,包括几个文件夹、几个虚拟目录和一个Tomcat主机。
在Java 8上运行Tomcat 8(8.0.46)时,一切正常。在升级到JDK 9 (OpenJDK 64位服务器VM(构建9.0.4+11,混合模式))之后,我们注意到每个servlet都被初始化了几次(即init(ServletConfig)方法被执行了几次),第一次是在主机上下文中(如预期的那样),并为站点中的每个文件夹修改一次。
不希望的副作用是servlet创建的临时文件/日志在站点的每个文件夹中都是重复的。

Tomcat server.xml包含Host定义:

<Host name="localhost" appBase="C:/Program Files (x86)/b4/Controller/bin/webserver/ebsc_web"
unpackWARs="true" autoDeploy="true">
<Context path="/servlets" docBase="C:/Program Files (x86)/b4/Controller/bin/webserverebsc_web"  xmlValidation="false" xmlNamespaceAware="false">
<WatchedResource>WEB-INF/web.xml</WatchedResource>
</Context>
<!--
<Valve className="org.apache.catalina.authenticator.SingleSignOn" />
-->
<!-- Access log processes all example.
Documentation at: /docs/config/valve.html
Note: The pattern used is equivalent to using pattern="common" -->
<Valve className="org.apache.catalina.valves.AccessLogValve" directory="logs"
prefix="localhost_access_log" suffix=".txt"
pattern="%h %l %u %t &quot;%r&quot; %s %b" />
</Host>

相同的位置(C:Program Files (x86)b4Controllerbinwebserverebsc_web)是Web站点的物理路径,并包含子文件夹,例如:applet、images等。启动Tomcat时,在默认位置(ebsc_web)创建日志,并在每个子文件夹中复制日志。

我们注意到当servlet在正确的servlet上下文中初始化时,堆栈是:

Daemon Thread [localhost-startStop-1] (Suspended (breakpoint at line 49 in UpdateSchedulerLoader))  
owns: StandardWrapper  (id=63)  
owns: StandardContext  (id=64)  
UpdateSchedulerLoader.init(ServletConfig) line: 49  
StandardWrapper.initServlet(Servlet) line: 1227 
StandardWrapper.loadServlet() line: 1140    
StandardWrapper.load() line: 1027   
StandardContext.loadOnStartup(Container[]) line: 5038   
StandardContext.startInternal() line: 5348  
StandardContext(LifecycleBase).start() line: 145    
ContainerBase$StartChild.call() line: 1408  
ContainerBase$StartChild.call() line: 1398  
FutureTask<V>.run() line: 264   
ThreadPoolExecutor.runWorker(ThreadPoolExecutor$Worker) line: 1167  
ThreadPoolExecutor$Worker.run() line: 641   
Thread.run() line: 844  

,但在以下任何时候,当它用指向子文件夹的servlet上下文初始化时,堆栈为:

Daemon Thread [localhost-startStop-1] (Suspended (breakpoint at line 42 in UpdateSchedulerLoader))  
owns: StandardWrapper  (id=154) 
owns: StandardContext  (id=144) 
UpdateSchedulerLoader.init(ServletConfig) line: 42  
StandardWrapper.initServlet(Servlet) line: 1227 
StandardWrapper.loadServlet() line: 1140    
StandardWrapper.load() line: 1027   
StandardContext.loadOnStartup(Container[]) line: 5038   
StandardContext.startInternal() line: 5348  
StandardContext(LifecycleBase).start() line: 145    
StandardHost(ContainerBase).addChildInternal(Container) line: 753   
StandardHost(ContainerBase).addChild(Container) line: 729   
StandardHost.addChild(Container) line: 717  
HostConfig.deployDirectory(ContextName, File) line: 1129    
HostConfig$DeployDirectory.run() line: 1871 
Executors$RunnableAdapter<T>.call() line: 514   
FutureTask<V>.run() line: 264   
ThreadPoolExecutor.runWorker(ThreadPoolExecutor$Worker) line: 1167  
ThreadPoolExecutor$Worker.run() line: 641   
Thread.run() line: 844  

所以servlet第一次由ContainerBase$StartChild.call()初始化,后来由HostConfig.deployDirectory(ContextName, File)初始化…

你能解释/修复这个行为吗?

根据@PiotrP的指示,问题解决了。在server.xml的Host configuration中设置两个autoDeploy="false" deployOnStartup="false"

相关内容

  • 没有找到相关文章

最新更新