如果我有需要在我的 webapp 和 Tomcat 之间共享的类(例如自定义领域和主体),包含这些类的 .jar 文件应该放在哪里?
目前我将 .jar 放在 ${CATALINA_HOME}/lib 中。当从相同类型的类分配引用时,此结果是 ClassCastException。这是一个例子:
MyCustomPrincipal principal = (MyCustomPrincipal)FacesContext.getCurrentInstance().getExternalContext().getUserPrincipal();
上述方法抛出 ClassCastException。该方法返回一个实际的 MyCustomPrincipal 类型(因为这是我的自定义领域在执行身份验证时赋予 Tomcat 的类型),显然,它是由不同的类加载器创建的。我该如何解决这个问题,以便 Tomcat 和我的 Web 应用程序都可以使用 MyCustomPrincipal?
http://tomcat.apache.org/tomcat-6.0-doc/class-loader-howto.html
感谢任何帮助。 安德鲁
最佳答案
看起来您加载了 2 个副本,一次在 tomcat 中,一次在您的 WEB-INF/lib jar 或已部署应用程序的其他类路径中。
您获得类路径异常的原因在于 WAR 查找类的方式。与普通的 Java 规则相反,war 首先在 war 内部查找一个类,然后才将请求传递给父类加载器。
一个类的标识依赖于类加载器,在一个类加载器中加载的同一个类在另一个类加载器中转换时会产生类转换异常。
解决方案是确保war 不包含应由容器提供的类。如果您使用 Maven,您可以将这些依赖项标记为“已提供”,如果您使用 Ant,则必须将类路径列表分成 2 部分并针对两者进行编译,但仅使用构建 war 所需的那些。
关于java - 类加载器和与 Apache Tomcat 共享 .jar 文件,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/3076959/