我有一个webapp,它使用一个监听器来动态添加servlet实例。 每个servlet实例由用户定义的配置文件定义,并封装不同的数据集。这些数据集中的每一个还可以包括一些用户定义的静态web文件(HTML,JPG,CSS等)。 每个servlet实例的静态资源都存储在webapp文件夹之外(以避免在重新部署时删除),并且每个servlet实例都有一个单独的文件夹层次结构。
在监听器contextInitialized方法中,我正在使用 javax.servlet.ServletContext.addServlet 添加我的每个servlet实例,以及 javax.servlet.ServletRegistration.Dynamic.addMapping 添加此servlet的URL映射。
我想为外部文件夹中的静态内容添加其他映射。 在Tomcat 7中,我扩展了org.apache.catalina.servlets.DefaultServlet 将relativePath更改为我的新文档根目录,但此类 在Tomcat 8 0中无效 - ClassNotFoundException(org.apache.naming.resources.FileDirContext)。
Tomcat 8有一个新的“资源”框架,应该让这更加直截了当。
我的问题是 - 如何在不编辑web.xml的情况下动态地(在我的侦听器内的Web应用程序启动时)向我的上下文添加PostResources元素?
在我的听众中,我应该能够做到这样的事情:
WebResourceRoot root = new StandardRoot(context);
root.createWebResourceSet(WebResourceRoot.ResourceSetType.POST,
"/my/url", "my/filesystem/path", null, "/");
但我无法弄清楚如何获取所需的上下文(org.apache.catalina.Context),这是与侦听器contextInitialized方法中ServletContextEvent提供的类似命名的javax.servlet.ServletContext完全不同的类型。 / p>
有什么建议吗? 感谢。
答案 0 :(得分:0)
我想我已经使用MBeanServer找到了它。 这似乎是一种迂回的方法 - 有没有办法从ServletContext获取StandardRoot或StandardContext对象?
import javax.management.MBeanServer;
import javax.management.MBeanServerFactory;
import javax.management.ObjectName;
import javax.servlet.ServletContext;
import org.apache.catalina.core.StandardContext;
import org.apache.catalina.core.StandardEngine;
import org.apache.catalina.Container;
import org.apache.catalina.Server;
import org.apache.catalina.Service;
import org.apache.catalina.WebResourceRoot;
...
private void addPostResources(ServletContext servletContext)
throws Exception /* just for debugging */ {
MBeanServer mbs = MBeanServerFactory.findMBeanServer(null).get(0);
ObjectName name = new ObjectName("Catalina","type","Server");
Server server = (Server)mbs.getAttribute(name, "managedResource");
Service service = server.findService("Catalina");
StandardEngine engine = service.getContainer();
Container hostContainer = engine.findChild(engine.getDefaultHost());
StandardContext standardContext = (StandardContext)hostContainer.findChild(servletContext.getContextPath());
WebResourceRoot root = standardContext.getResources();
root.createWebResourceSet(WebResourceRoot.ResourceSetType.POST,
"/my/url", "my/filesystem/path", null, "/");
}