我正在使用JAASRealm身份验证(在tomcat 7中)。 这是servlet的过滤器:
private String loginPage = "welcome.jsp";
@Override
public void doFilter(ServletRequest request, ServletResponse response,
FilterChain filterChain) throws IOException, ServletException {
if ((request instanceof HttpServletRequest) && (response instanceof HttpServletResponse)) {
HttpServletRequest httpServletRequest = (HttpServletRequest) request;
HttpServletResponse httpServletResponse = (HttpServletResponse) response;
if (httpServletRequest.getUserPrincipal() == null) {
// User is not logged in, redirect to login page.
httpServletRequest.setAttribute("from", httpServletRequest.getRequestURI());
httpServletResponse.sendRedirect(loginPage);
}
else {
filterChain.doFilter(request, response);
}
}
}
我在web.xml中声明了它
<filter>
<filter-name>login-filter</filter-name>
<filter-class>LoginFilter</filter-class>
</filter>
<filter-mapping>
<filter-name>login-filter</filter-name>
<url-pattern>/sampleServlet</url-pattern>
</filter-mapping>
我的问题是当我没有通过身份验证并且我通过AJAX调用servlet时,这行过滤器不起作用
httpServletResponse.sendRedirect(loginPage);
所以,我没有收到任何数据,我没有被重定向到登录页面。在这种情况下我该怎么办?
答案 0 :(得分:7)
我尝试使用一些优雅的解决方案,但都没有效果。我发现这一个吃了primefaces论坛,并且还在纯JSF应用程序上工作。
我使用了网络过滤器:
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
HttpServletRequest httpRequest = (HttpServletRequest) request;
HttpServletResponse httpResponse = (HttpServletResponse) response;
if(!identity.isLoggedIn()){
if (isAjax(httpRequest)) {
httpResponse.getWriter().print(xmlPartialRedirectToPage(httpRequest, "/login.xhtml"));
httpResponse.flushBuffer();
}else{
httpResponse.sendRedirect(httpRequest.getContextPath() + "/login.xhtml");
}
}else{
chain.doFilter(request, response);
}
}
private String xmlPartialRedirectToPage(HttpServletRequest request, String page) {
StringBuilder sb = new StringBuilder();
sb.append("<?xml version='1.0' encoding='UTF-8'?>");
sb.append("<partial-response><redirect url=\"").append(request.getContextPath()).append(request.getServletPath()).append(page).append("\"/></partial-response>");
return sb.toString();
}
private boolean isAjax(HttpServletRequest request) {
return "XMLHttpRequest".equals(request.getHeader("X-Requested-With"));
}
答案 1 :(得分:2)
以下是我在过滤AJAX请求时发送重定向的方式......
AJAX代码(jQuery)
$.ajax({
type: 'post',
url: '/signMeInServlet',
data: {
'name': name,
'pass': passW,
},
dataType: 'json',
success: processSignInReturnMethod,
error: function (xhr, ajaxOptions, thrownError){
if (thrownError.redirect.length) {
window.location.replace(thrownError.redirect);
} else {
alert('There was an error processing your request, please try again');
}
}
});
相关过滤器代码
// Rest of your Filter processing and logic here, once you know you want
// to redirect, use the below code, which works for both AJAX and regualar
// requests
HttpServletRequest hreq = (HttpServletRequest) request;
String redirectUrl = "/redirected.jsp";
if (hreq.getHeader("x-requested-with") != null &&
hreq.getHeader("x-requested-with").equalsIgnoreCase("XMLHttpRequest")) {
// Set up your response here
HttpServletResponse hres = (HttpServletResponse) response;
hres.setContentType("text/json; charset=UTF-8");
PrintWriter out = hres.getWriter();
String json = "[{\"redirect\":\"" + redirectUrl + "\"}]";
out.write(json);
out.flush();
out.close();
} else {
((HttpServletResponse)response).sendRedirect(redirectUrl);
}
答案 2 :(得分:0)
我解决了这个问题,但没有像我一样。 我在servler-filter中使用了这一行
httpServletResponse.setStatus(HttpServletResponse.SC_MOVED_PERMANENTLY);
并在客户端,使用ajax请求我捕获此状态,然后我执行重定向
var fAjaxRedirect = function(response, textStatus) {
/* 301 is the code SC_MOVED_PERMANENTLY */
if (response.status == 301) {
location.reload(); //or location.href = 'xxxx.jsp';
}};
$.ajaxSetup({
scriptCharset: "utf-8",
contentType: "application/x-www-form-urlencoded; charset=UTF-8"
});
$.ajax({
type: "POST",
url: "myServlet",
complete: fAjaxRedirect,
success: function(val) {
//something here
}
});
但是使用这种方式,是执行页面重定向的客户端,我想从服务器执行此操作,而不是依赖于客户端。