cod*_*247 4 java tomcat servlets tomcat6
当我尝试从请求中获取会话时,如果会话过期,则会导致空指针异常.以下是代码的一部分.我在第三行得到例外.
public void doFilter(ServletRequest req, ServletResponse res,FilterChain chain) throws IOException, ServletException {
HttpServletRequest httpReq = (HttpServletRequest) req;
HttpSession session = httpReq.getSession(false);
Run Code Online (Sandbox Code Playgroud)
这是堆栈跟踪:
java.lang.IllegalStateException: getLastAccessedTime: Session already invalidated
at org.apache.catalina.session.StandardSession.getLastAccessedTime(StandardSession.java:423)
at org.apache.catalina.session.StandardSessionFacade.getLastAccessedTime(StandardSessionFacade.java:84)
at com.myapp.admin.CustomerContext.valueUnbound(CustomerContext.java:806)
at org.apache.catalina.session.StandardSession.removeAttributeInternal(StandardSession.java:1686)
at org.apache.catalina.session.StandardSession.expire(StandardSession.java:801)
at org.apache.catalina.session.StandardSession.isValid(StandardSession.java:576)
at org.apache.catalina.connector.Request.doGetSession(Request.java:2386)
at org.apache.catalina.connector.Request.getSession(Request.java:2120)
at org.apache.catalina.connector.RequestFacade.getSession(RequestFacade.java:833)
at com.myapp.ui.web.filter.ApplicationSessionFilter.doFilter(ApplicationSessionFilter.java:45)
at org.springframework.web.filter.DelegatingFilterProxy.invokeDelegate(DelegatingFilterProxy.java:237)
at org.springframework.web.filter.DelegatingFilterProxy.doFilter(DelegatingFilterProxy.java:167)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:235)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206)
at com.myapp.ui.web.filter.ErrorFilter.doFilter(ErrorFilter.java:42)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:235)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206)
at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:233)
at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:191)
at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:127)
at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:102)
at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:109)
at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:298)
at org.apache.jk.server.JkCoyoteHandler.invoke(JkCoyoteHandler.java:190)
at org.apache.jk.common.HandlerRequest.invoke(HandlerRequest.java:291)
at org.apache.jk.common.ChannelSocket.invoke(ChannelSocket.java:776)
at org.apache.jk.common.ChannelSocket.processConnection(ChannelSocket.java:705)
at org.apache.jk.common.ChannelSocket$SocketConnection.runIt(ChannelSocket.java:898)
at org.apache.tomcat.util.threads.ThreadPool$ControlRunnable.run(ThreadPool.java:690)
at java.lang.Thread.run(Thread.java:662)
Run Code Online (Sandbox Code Playgroud)
这不是Nullpointer异常.
这是一个非法的例外情况.
当会话失效/过期并且您尝试访问它时会发生这种情况.
会话失效如下.
session.invalidate();
Run Code Online (Sandbox Code Playgroud)
调用invalidate后,您无法使用该会话.
会话超时后到期.它们到期后,如果您尝试使用它,它将抛出相同的异常.
这些是您可以手动设置超时的方法.
在web.xml中设置超时.这是在几分钟内设定的.
<session-config>
<session-timeout>30</session-timeout>
</session-config>
Run Code Online (Sandbox Code Playgroud)
或者你也可以在java中设置它.
public void setMaxInactiveInterval(int interval)
session.setMaxInactiveInterval(30*60); // This we set in seconds.
Run Code Online (Sandbox Code Playgroud)
这里我们指定servlet容器使此会话无效之前客户端请求之间的时间(以秒为单位).否定时间表示会话永远不会超时.
确保您正在执行的操作不会超过超时时间.否则,您将不得不重置该值.
编辑:
无法以干净的方式从中恢复.会话将失效/不可用,您将需要创建一个新会话并重新填充数据.通常,人们被重定向到备用错误PAge而不是显示堆栈跟踪."您的会话已过期.请重新登录."
使用request.isRequestedSessionIdValid()来标识会话ID是否仍然有效.
HttpSession session =httpReg.getSession(false);
if( !request.isRequestedSessionIdValid() )
{
//comes here when session is invalid.
// redirect to a clean error page "Your session has expired. Please login again."
}
Run Code Online (Sandbox Code Playgroud)
另一种选择是使用try catch来处理IllegalExceptionState
HttpSession session =httpReg.getSession(false);
try
{
if(session != null)
{
Date date = new Date(session.getLastAccessedTime());
}
}
catch( IllegalStateException ex )
{
//comes here when session is invalid.
// redirect to a clean error page "Your session has expired. Please login again."
}
Run Code Online (Sandbox Code Playgroud)
旁注:如果确实有一个过程需要很长时间才能完成并且会话超时(例如:解析非常大的数据记录).您应该考虑将它们从Web应用程序中取出,并使用简单的Java将它们作为一个进程运行.
| 归档时间: |
|
| 查看次数: |
9956 次 |
| 最近记录: |