我试图让Tomcat在关机时坚持我的会话。我已经处理了我在会话中存储的所有内容都是可序列化的要求,当我在Eclipse下运行Tomcat时,这很好用:当代码更改迫使Eclipse重新加载webapp时,会话现在可以存活。
然而,当我尝试在独立的Tomcat中做同样的事情时,我遇到了一个问题。
我在$ {catalina.base} /conf/context.xml中取消了对Manager元素的注释,并将pathname属性设置为$ {catalina.base} /SESSIONS.ser,在关闭时,我看到了SESSIONS。服务器文件出现。到目前为止,非常好。
但是当我重新启动Tomcat时,它出现在catalina.out中:
[...]
06-Apr-2017 13:39:52.570 SEVERE [localhost-startStop-1] org.apache.catalina.session.StandardManager.startInternal Exception loading sessions from persistent storage
java.lang.ClassNotFoundException: com.mycompany.wtt.util.LogoutLogger
at org.apache.catalina.loader.WebappClassLoaderBase.loadClass(WebappClassLoaderBase.java:1285)
[...]
06-Apr-2017 13:39:54.158 INFO [localhost-startStop-1] org.apache.catalina.startup.HostConfig.deployWAR Deployment of web application archive /data/tokken/apache-tomcat-8.5.12/webapps/wtt.war has finished in 1,134 ms
[...]
com.mycompany.wtt.util.LogoutLogger类是wtt.war webapp的一部分,显然,Tomcat尝试在加载webapp之前反序列化webapp的会话。看起来这意味着我无法在我的会话中放置特定于应用程序的类,这是一个很大的问题,因为我的一些逻辑依赖于能够做到这一点,并通过实现创建自定义行为javax.servlet.http.HttpSessionActivationListener。
有没有办法让Tomcat在加载webapps后反序列化会话?
版本:Tomcat 8.5.12,Java 1.8.0_121。
答案 0 :(得分:0)
事实证明问题是在全局Manager
中使用绝对路径配置context.xml
。这意味着当Tomcat读取序列化会话时,它不知道它属于哪个webapp,显然它只是尝试加载它(进入它部署的第一个webapp?),并且由于特定于应用程序而失败类。
我通过将${catalina.home}/conf/context.xml
更改回其原始状态并将Manager元素注释掉,然后在webapp的<Manager pathname="${catalina.home}/sessions/wtt.ser">
中添加META-INF/context.xml
来实现它。< / p>
请注意,如果您只是说pathname="SESSIONS.ser"
,那么您的会话将在服务器重新启动后继续存在,但它们将无法在重新部署应用程序时继续存在,因为后者会破坏应用程序的工作目录,这就是会话存储相对路径名。说pathname="${catalina.home}/sessions/wtt.ser"
可以避免这种情况(但请确保您希望会话的任何目录提前存在,因为Tomcat不会为您创建它)。