问题描述
我需要了解为什么使用下面的代码向嵌入式 tomcat 动态添加 webapp 会出现以下错误,当我们在启动时添加 Context 时一切正常,代码是相同的。 代码:
data
我们得到的错误是:
/*
* Add a context to the host and contexts map; be careful to call this only
* within a synchronization block of this.contexts
*/
private Context addContextDynamically(String contextpath,String folderName) {
logger.info("Adding context " + contextpath + " at " + folderName);
Context contextNew = this.embedded.addWebapp(this.host,contextpath,folderName);
// Context contextNew = this.embedded.addContext(this.host,// folderName);
// this.embedded.addContext(host,dir)
// logger.info("contextNew-->"+contextNew);
List<File> filterdJarfiles = getappjarFilesAlone(folderName);
WebResourceRoot resources = new StandardRoot(contextNew);
for (File jf : filterdJarfiles) {
String st = jf.getAbsolutePath().substring(0,jf.getAbsolutePath().lastIndexOf(File.separator));
logger.info("st-->"+st);
resources.addPreResources(new DirResourceSet(resources,"/WEB-INF/lib",st,"/"));
}
logger.fine("Adding context setResources " + resources);
logger.fine("Adding context contextNew "+ contextNew);
logger.fine("Adding context filterdJarfiles " + filterdJarfiles.toString());
try {
contexts.put(contextNew.getPath(),contextNew);
contextNew.setResources(resources);
INexxWebappLoader loader = new INexxWebappLoader(contextNew.getParentClassLoader(),contextNew);
contextNew.setLoader(loader);
// host.addChild(context);
cleanContextworkdir((StandardContext) contextNew);
}catch (Exception e) {
logger.info("Caught exception while adding context :"+ e.getLocalizedMessage());
e.printstacktrace();
}
return contextNew;
}
所以基本上我们的产品会下载 zip 文件并将其解压缩到我们设置的 web 应用程序目录和 server.xml 中:
java.lang.IllegalStateException: Error starting static Resources
at org.apache.catalina.core.StandardContext.setResources(StandardContext.java:2470)
at com.medicity.iNexx.AppServer.addContextDynamically(AppServer.java:541)
at com.medicity.iNexx.AppServer.monitorEnablements(AppServer.java:439)
at com.medicity.iNexx.AppServer.run(AppServer.java:345)
at com.medicity.iNexx.AppServer.init(AppServer.java:244)
at com.medicity.iNexx.AppServer.main(AppServer.java:335)
解决方法
如果您将 Context
添加到正在运行的 Host
,它将自动启动,除非 startChildren
组件上的属性 false
设置为 Host
.您可能不希望这样,因为您的 addContextDynamically
需要先配置上下文。
因此在用于配置Tomcat的方法中需要调用:
final Host host = this.embedded.getHost()
if (host instanceof ContainerBase) {
((ContainerBase) host).setStartChildren(false);
}
并且您需要添加到 addContextDynamically
:
final State hostState = this.embedded.getHost().getState();
if (hostState.isAvailable() || LifecycleState.STARTING_PREP.equals(hostState)) {
contextNew.start();
}
参见source code 了解更多信息。
备注:在 Host
开始之前添加的上下文不受 startChildren
属性的影响。