我们在访问一些网站的时候,登陆一次以后,一般在关闭浏览器前,这个网站都会保持我们的登陆状态,并且显示登陆后才能看到的信息,下面我们来实现这个功能。
一、准备用户数据
编写User类
public class User {
private String username;
private String password;
public User() {
super();
// TODO Auto-generated constructor stub
}
public User(String username, String password) {
super();
this.username = username;
this.password = password;
}
public String getUsername() {
return username;
}
public void setUsername(String username) {
this.username = username;
}
public String getPassword() {
return password;
}
public void setPassword(String password) {
this.password = password;
}
// 我们后面会用到equals方法,在这里先进行重写
@Override
public boolean equals(Object obj) {
if (this == obj)
return true;
if (obj == null)
return false;
if (getClass() != obj.getClass())
return false;
User other = (User) obj;
if (password == null) {
if (other.password != null)
return false;
} else if (!password.equals(other.password))
return false;
if (username == null) {
if (other.username != null)
return false;
} else if (!username.equals(other.username))
return false;
return true;
}
}
编写UserDB类,模拟数据库
import java.util.ArrayList;
import java.util.List;
public class UserDB {
private static List users = new ArrayList();
static{
users.add(new User("zhangsan","123456"));
users.add(new User("lisi","654321"));
}
public static List getUsers(){
return users;
}
}
第二步:实现登陆和注销功能
创建LoginServlet,实现登陆功能
import java.io.IOException;
import java.io.PrintWriter;
import java.util.List;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import com.itheima.domain.User;
import com.itheima.domain.UserDB;
public class LoginServlet extends HttpServlet {
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
//获取字符输出流
PrintWriter out = response.getWriter();
//获取用户名和密码,创建用户对象
String username = request.getParameter("username");
String password = request.getParameter("password");
User user = new User(username,password);
//获取所有的用户数据
List users = UserDB.getUsers();
//判断是否有该用户
if(users.contains(user)){
out.println("登陆成功!3秒后跳转到首页");
response.setHeader("Refresh", "3;URL=/web11_2/index.jsp");
//创建一个session域对象,记录用户登陆状态
HttpSession session = request.getSession();
session.setAttribute("user",user);
}else{
out.println("用户名或密码错误!3秒后跳转到登陆页面");
response.setHeader("Refresh", "3;URL=/web11_2/login.jsp");
}
}
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
// TODO Auto-generated method stub
doGet(request, response);
}
}
创建LogoutServlet,实现注销功能
import java.io.IOException;
import java.io.PrintWriter;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
public class LogoutServlet extends HttpServlet {
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
//获取字符输出流对象
PrintWriter out = response.getWriter();
//获取session对象
HttpSession session = request.getSession();
session.invalidate();
out.println("注销成功!3秒后跳转到首页");
response.setHeader("Refresh", "3;URL=/web11_2/index.jsp");
}
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
// TODO Auto-generated method stub
doGet(request, response);
}
}
第三步:创建首页、登陆页面以及个人信息页面
编写index.jsp
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
Insert title here
首页
欢迎${user.username}登陆!
注销
登陆
编写login.jsp
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
Insert title here
登陆界面
个人信息页面
我们在WebContent文件夹下创建一个important文件夹,将个人信息页面放入文件夹中,这里不再详细编写个人信息页面,读者可以自行编写。
Insert title here
这是个人信息页面!
第四步:创建一个Filter,并修改拦截范围
我们在访问网站时,需要登录后才能看到我们的个人信息,否则我们的个人信息就回泄露,所以我们应该设置一个跟权限有关的Filter,只有登录以后才能访问个人信息页面,同时应该对Filter的拦截范围进行设置,只对访问的个人信息页面进行拦截。
创建Filter
import java.io.IOException;
import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
public class PrivilegeFilter implements Filter {
public PrivilegeFilter() {
// TODO Auto-generated constructor stub
}
public void destroy() {
// TODO Auto-generated method stub
}
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
HttpServletRequest req = (HttpServletRequest) request;
HttpServletResponse res = (HttpServletResponse) response;
//获取session对象
HttpSession session = req.getSession();
Object obj = session.getAttribute("user");
//判断用户是否登陆
if(obj != null){
//用户已经登录,放行
chain.doFilter(req, res);
}else {
//用户没有登录,给出提示并跳转到登陆页面
res.getWriter().println("请先登录!3秒后跳转到登陆界面");
res.setHeader("Refresh", "3;URL=/web11_2/login2.jsp");
}
}
public void init(FilterConfig fConfig) throws ServletException {
// TODO Auto-generated method stub
}
}
修改配置文件,只对重要的信息访问进行拦截
PrivilegeFilter
PrivilegeFilter
com.itheima.filter.PrivilegeFilter
PrivilegeFilter
/important/*
注意:
配置信息必须放在设置字符编码拦截器之后,否则会出现乱码问题。
我们将对检验登陆状态的拦截器放到解决编码的拦截器后就可以解决这个问题,所以我们在写拦截器的时候要注意逻辑顺序。
第五步:处理缓存问题
完成上面的四步后,我们测试会发现,在注销后,我们仍然可以方法个人信息页面,这是因为存在缓存的原因,所以我们要设置缓存的时间。
创建一个拦截器,修改缓存时间
import java.io.IOException;
import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletResponse;
public class NoCashFilter implements Filter {
public void destroy() {
// TODO Auto-generated method stub
}
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
HttpServletResponse res = (HttpServletResponse) response;
res.setDateHeader("Expires", -1);//告诉浏览器可以缓存多长时间 -1 或者 0 表示不缓存
res.setHeader("Cache_Control", "no-cache");//支持http1.1 告诉浏览器不要缓存
res.setHeader("Pragma", "no-cache");//支持http1.0 告诉浏览器不要缓存
chain.doFilter(request, res);
}
public void init(FilterConfig fConfig) throws ServletException {
// TODO Auto-generated method stub
}
}
修改配置文件,只对重要的信息访问进行拦截
NoCashFilter
NoCashFilter
com.itheima.filter.NoCashFilter
NoCashFilter
/important/*
案例结果:
首页
使用错误的信息登录
正确登录
查看个人信息
返回,注销登录
再次访问个人信息