最近在做一个filter验证cookie的时候遇到了一些问题,目前已解决,记录一下。
先说第一个问题,filter不报错,网页控制台也不报错,但是跳转页面空白
代码如下
public void doFilter(ServletRequest arg0, ServletResponse arg1, FilterChain arg2)
throws IOException, ServletException {
// TODO 自动生成的方法存根
HttpServletRequest req=(HttpServletRequest)arg0;
HttpServletResponse resp=(HttpServletResponse)arg1;
SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss:SSS");//设置日期格式
System.out.println(df.format(new Date())+"--"+"进入文件判断!");
Cookie[] cookies=req.getCookies();
String user_name = "";
String passwd = "";
if(cookies!=null){
System.out.println(df.format(new Date())+"--"+"存在cookie");
for(Cookie coo:cookies){
System.out.println(df.format(new Date())+"--"+"cookiename:"+coo.getName());
if(coo.getName().equals("user")){
System.out.println(df.format(new Date())+"--"+"存在usercookie");
String[] info_cookie=coo.getValue().split("-");
user_name=info_cookie[0];
passwd=info_cookie[1];
//如果在cookie中得到保存的用户名和密码,验证正确后,直接转到success页
if(Check_Name_Pass_Sql.select_sql(user_name, passwd)==2){
System.out.println(df.format(new Date())+"--"+"通过cookie进入,返回成功页面");
req.getRequestDispatcher("../test.jsp").forward(req, resp);
}else{
arg2.doFilter(req, resp);
}
}
}
}else{
arg2.doFilter(req, resp);
}
}
这个代码问题在于,当cookie中没有名为user的时候,没有加else跳转放行,导致了网页没有跳转方向,所以出现空白,遇到跳转空白的时候要检查代码逻辑判断是否有跳转
但是当我加上else的时候,又出现报错Cannot forward after response has been comm,代码如下
if(cookies!=null){
System.out.println(df.format(new Date())+"--"+"存在cookie");
for(Cookie coo:cookies){
System.out.println(df.format(new Date())+"--"+"cookiename:"+coo.getName());
if(coo.getName().equals("user")){
System.out.println(df.format(new Date())+"--"+"存在usercookie");
String[] info_cookie=coo.getValue().split("-");
user_name=info_cookie[0];
passwd=info_cookie[1];
//如果在cookie中得到保存的用户名和密码,验证正确后,直接转到success页
if(Check_Name_Pass_Sql.select_sql(user_name, passwd)==2){
System.out.println(df.format(new Date())+"--"+"通过cookie进入,返回成功页面");
req.getRequestDispatcher("../test.jsp").forward(req, resp);
}else{
arg2.doFilter(req, resp);
}
}else{
arg2.doFilter(req, resp);
}
}
}else{
arg2.doFilter(req, resp);
}
这里在判断是否存在user这个名字cookie的时候加上了else跳转,但是也会报错,百度说是产生了两次跳转,在每一次跳转后加上return,我加上之后发现又是跳转空白页面。
于是就分析了一下原因如下,
(不加return报错原因)
这个代码是用for循环一边遍历cookie,一边验证cookie,当你请求网页的cookie有两个以上,第一个cookie的名字与判断不符合,于是产生了跳转但是这个时候没有return,程序还在运行,继续遍历第二个cookie,当第二个cookie判断匹配成功,于是跳转指定页面,这个就产生了两次跳转
所以程序报错Cannot forward after response has been comm。
(加上return)
这个代码在每个else跳转后加上return之后,如果第一个cookie判断不匹配,就放行跳转,接着return结束,这时候程序就终止了,也就不会遍历剩下的cookie了,所以页面产生空白。
下面就是改进代码。
不在遍历的时候同时判断,即先遍历cookie存储在一个集合或者数组里面,遍历完成后再进行判断,这样就不会存在上述问题。
public void doFilter(ServletRequest arg0, ServletResponse arg1, FilterChain arg2)
throws IOException, ServletException {
// TODO 自动生成的方法存根
HttpServletRequest req=(HttpServletRequest)arg0;
HttpServletResponse resp=(HttpServletResponse)arg1;
SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss:SSS");//设置日期格式
SimpleDateFormat data = new SimpleDateFormat("yyyy-MM-dd");//设置log文件名格式
String Date=data.format(new Date());
//默认输出在eclipse控制台
//本地tomcat输出路径
//System.setOut(new PrintStream(new FileOutputStream("../webapps/test_one/logs/"+Date+"--log.txt",true),true));
//服务器输出路径
//System.setOut(new PrintStream(new FileOutputStream("/www/server/tomcat/webapps/test_one/logs/"+Date+"--log.txt",true),true));
System.out.println(df.format(new Date())+"--"+"进入文件判断!");
//获取所有cookie
Cookie[] cookies=req.getCookies();
//存储cookie名字集合
ArrayList<String> cookie_name=new ArrayList<String>();
//用户名
String user_name = "";
//用户密码
String passwd = "";
if(cookies!=null){
System.out.println(df.format(new Date())+"--"+"存在cookie");
for(Cookie coo:cookies){
System.out.println(df.format(new Date())+"--"+"cookiename:"+coo.getName());
//将所有cookie名字添加集合
cookie_name.add(coo.getName());
}
//判断cookie名字集合是否存在用户登录的cookie
if(cookie_name.contains("user")){
System.out.println(df.format(new Date())+"--"+"存在user-cookie");
String[] info_cookie=cookies[cookie_name.indexOf("user")].getValue().split("-");
//用UTF-8解析cookie
user_name=URLDecoder.decode(info_cookie[0], "utf-8");
passwd=info_cookie[1];
//如果在cookie中得到保存的用户名和密码,验证正确后,直接转到success页
if(Check_Name_Pass_Sql.select_sql(user_name, passwd)==2){
System.out.println(df.format(new Date())+"--"+"cookie验证成功,正在获取数据");
String[] info_all=select_all.selectAll(user_name);
//用户id
String id=info_all[0];
System.out.println(id);
//用户昵称
String name=info_all[1];
System.out.println(name);
//用户邮箱
String email=info_all[2];
System.out.println(email);
//用户性别
String sex=info_all[3];
System.out.println(sex);
//用户年龄
String age=info_all[4];
System.out.println(age);
//用户兴趣爱好
String interest=info_all[5];
System.out.println(interest);
//用户简介信息
String info=info_all[6];
System.out.println(info);
req.setAttribute("id", id);
req.setAttribute("name", name);
req.setAttribute("email", email);
req.setAttribute("sex", sex);
req.setAttribute("age", age);
req.setAttribute("interest", interest);
req.setAttribute("info", info);
//防止网页读取缓存
resp.addHeader("Pragma","no-cache");
resp.setHeader("Cache-Control","no-cache");
resp.setHeader("Expires","0");
System.out.println(df.format(new Date())+"--"+"通过cookie进入,返回成功页面");
req.getRequestDispatcher("/login_success.jsp?"+df.format(new Date())).forward(req, resp);
System.out.println(String.join("", Collections.nCopies(100, "-")));
return;//转发结束,终止当前程序
}else{
//cookie密码匹配错误,返回登录页面
resp.sendRedirect("http://localhost:8080/test_one/login/login.html?timestamp="+new Date().getTime());
return;
}
//cookie存在login_user,则进行下一步判断用户名验证信息
}else if (cookie_name.contains("login_user")) {
System.out.println(df.format(new Date())+"--"+"存在login_user的cookie");
String login_cookie=cookies[cookie_name.indexOf("login_user")].getValue();
//用户名存在,允许通过登录文件
if (login_cookie.equals("name_existed")) {
System.out.println(df.format(new Date())+"--"+"login_user的cookie验证通过");
arg2.doFilter(req, resp);
return;
}
else {//用户名不存在,不允许通过登录文件,返回登录页面
resp.sendRedirect("http://localhost:8080/test_one/login/login.html?timestamp="+new Date().getTime());
System.out.println(df.format(new Date())+"--"+"返回登录页面");
return;
}
} else{//两种cookie都没有,返回登录页面
resp.sendRedirect("http://localhost:8080/test_one/login/login.html?timestamp="+new Date().getTime());
System.out.println(df.format(new Date())+"--"+"返回登录页面");
return;
}
}else{//没有任何cookie,返回登录页面
resp.sendRedirect("http://localhost:8080/test_one/login/login.html?timestamp="+new Date().getTime());
return;
}
}
以上就是本次的记录,有问题可以留言讨论一下。