登录后才能访问一些页面,用过滤器实现(进行登录后才能用的操作之前系统都要自行认证身份)
package util;
import domain.User;
import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.ServletException;
import javax.servlet.http.HttpFilter;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
public class LoginFilter extends HttpFilter implements Filter {
@Override
protected void doFilter(HttpServletRequest request, HttpServletResponse response, FilterChain chain) throws IOException, ServletException {
//先排除不需要认证的请求
//自行登录操作不需要认证(需要用户手动认证)还有*.js *.jpg *.css
// request.getRequestURL();// http://localhost:8080/qxgl/login.view
// request.getRequestURI();// /qxgl/login.view
// request.getContextPath();// /qxgl工程名
String path = request.getServletPath();//获得此次请求 login.view
System.out.println("path:"+path);
if(path.contains("login")||(path.contains(".js")&&(!path.contains(".jsp")))||path.contains(".css")||path.contains(".jpg")){
//不需要认证,放过此次请求,继续请求目标
chain.doFilter(request,response);//放行
return;
}
//其余请求做登录认证
User user=(User) request.getSession().getAttribute("loginUser");
if(user==null){
//需要认证,但发现还没有登录
response.sendRedirect("http://localhost:8080/qxgl07/login.jsp");
}else {
//需要认证,且认证通过,放过请求,继续访问目标
chain.doFilter(request,response);
}
}
}
添加自动登录功能
将账号密码以及此次用户请求的一些信息存储在服务端
用户本身的信息
用户访问的ip信息(mac)
用户浏览器信息
并为之生成一个令牌,将令牌随着cookie响应给浏览器,浏览器每次请求时都会传递cookie(令牌)
每次请求前都要验证一下:是否需要自动登录,是否已经登陆**
package util;
import domain.Token;
import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.ServletException;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpFilter;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
//自动登录过滤器
public class AutoLoginFilter extends HttpFilter implements Filter {
@Override
protected void doFilter(HttpServletRequest request, HttpServletResponse response, FilterChain chain) throws IOException, ServletException {
String path = request.getServletPath();
if ((path.endsWith(".js")) || path.contains(".css") || path.contains(".jpg")) {
//不需要认证,放过此次请求,继续请求目标
chain.doFilter(request, response);//放行
return;
}
Cookie[] cookies = request.getCookies();
if (cookies != null && cookies.length > 0) {//有cookie
for (Cookie c : cookies) {
String name = c.getName();
String value = c.getValue();//tokenId值
if ("tokenId".equals(name)) {
//value==uuid,有自动登录处理
Token token = (Token) request.getServletContext().getAttribute(value);
if (token == null) {
//伪造的tokenId,不能自动登录
chain.doFilter(request, response);
return;
} else if (!token.getIp().equals(request.getRemoteAddr())) {//ip地址不一样
chain.doFilter(request, response);
return;
} else if (token.getEnd() < System.currentTimeMillis()) {//已经超过自动登录时效
chain.doFilter(request, response);
return;
} else {//符合自动登录条件
request.getSession().setAttribute("loginUser", token.getUser());
if (path.contains("login.jsp")) {//此次请求正要访问登录页,但已经实现自动登录,所以直接跳转到主界面
response.sendRedirect("http://localhost:8080/qxgl07/main.jsp");
return;
}
chain.doFilter(request, response);
return;
}
}
}
}
chain.doFilter(request, response);
}
}
package domain;
//自动登录的令牌验证信息
public class Token {
private String token;//uuid
private User user;
private String ip;
private long start;//生效时间戳,单位为毫秒
private long end;//失效时间戳
public Token() {}
public Token(String token, User user, String ip, long start, long end) {
this.token = token;
this.user = user;
this.ip = ip;
this.start = start;
this.end = end;
}
public String getToken() {
return token;
}
public User getUser() {
return user;
}
public String getIp() {
return ip;
}
public long getStart() {
return start;
}
public long getEnd() {
return end;
}
public void setToken(String token) {
this.token = token;
}
public void setUser(User user) {
this.user = user;
}
public void setIp(String ip) {
this.ip = ip;
}
public void setStart(long start) {
this.start = start;
}
public void setEnd(long end) {
this.end = end;
}
}
//自动登录实现
if(autoflag!=null&&!"".equals(autoflag)){
String tokenId= UUID.randomUUID().toString();
Cookie c=new Cookie("tokenId",tokenId);
c.setMaxAge(60);//cookie在浏览器的存活时间,秒为单位,时间应与后面一致
resp.addCookie(c);//传递令牌
Token token=new Token(tokenId,user,req.getRemoteAddr(),
System.currentTimeMillis(),
System.currentTimeMillis()+1000L*20);//七天就是加上1000L*60*60*24*7
//req.getRemoteAddr();可以获得局域网ip,广域网使用代理后还要其他方式获得
//token在服务器中如何存储?
//request和session都不行,数据库则有些浪费空间影响效率
//application(服务器运行期缓存),redis缓存中
req.getServletContext().setAttribute(tokenId,token);
}
**