有没有办法让页面的会话保持活动而不需要将状态发送到客户端?我无法将STATE_SAVING_METHOD
设置为client
,我宁愿不使用a4j:keepalive
。
我已经尝试使用提交给Bean的简单隐藏iframe,但它使主页无效。
我正在使用JSF 1.2和myfaces。
这是为了在不需要用户登录的页面上绕过ViewExpiredException。大多数现有站点都要求用户登录。
实施ajax轮询作为“心跳”以保持会话活跃。最简单的是你可以通过一点jQuery来实现这一目的,以避免100行的样板代码使其在世界上所知的所有不同浏览器中工作:
<script src="http://code.jquery.com/jquery-latest.min.js"></script>
<script>
$(document).ready(function() {
setInterval(function() {
$.get("${pageContext.request.contextPath}/poll");
}, ${(pageContext.session.maxInactiveInterval - 10) * 1000});
});
</script>
${pageContext.session.maxInactiveInterval}
根据服务器端配置打印会话尚未生存的剩余秒数(可以通过<session-timeout>
中的web.xml
控制),并且在10秒内被扣除,只是为了在它自动到期之前准时,并且转换为到毫秒,以便它适合setInterval()
期望的。
$.get()
在给定的URL上发送ajax GET请求。对于上面的示例,您需要在/poll
的URL模式上映射servlet,并在doGet()
方法中基本执行以下操作:
request.getSession(); // Keep session alive.
那应该是它。
BalusC's answer帮助我在我的应用程序中满足了这个要求,但由于我使用的是PrimeFaces,我想分享一下BalusC的答案如何启发我用来执行此操作的代码。
xhtml页面
<p:poll listener="#{pf_usersController.keepUserSessionAlive()}"
interval="#{session.maxInactiveInterval - 10}" />
豆
public void keepUserSessionAlive() {
FacesContext context = FacesContext.getCurrentInstance();
HttpServletRequest request = (HttpServletRequest) context.getExternalContext().getRequest();
request.getSession();
}
一如既往,谢谢你,BalusC!
编辑:最终用户今天早上对此进行了测试,它运行良好!我的应用程序通常在整页刷新后15分钟强制会话超时(通过基于session.maxInactiveInterval和web.xml中的会话超时值的元刷新重定向到sessionExpired.xhtml);如果用户在一个页面上执行一堆AJAX请求,会话将超时,因为AJAX!=整页刷新,但此代码允许最终用户“保持会话活动”,而最终用户在应用程序的工资单页面上,并且会话保持活动状态1到2个小时! :)