一、session介绍
1、概念
session是由服务器创建,并且保存在服务器端的会话技术
2、为什么还要使用session技术呢?
cookie服务器创建保存在客户端的技术,不够安全的
session服务器创建保存在服务器端的技术,相对的就会安全很多
3、关闭浏览器,session是否存在?
如果关闭浏览器,session是存在的
原因:关闭浏览器,cookie没了(cookie默认是一个会话级别的),保存在cookie里面的sessionID没了,获得不到数据
二、session操作
1、session的创建
默认情况,必须手动调用相关的方法来获得
HttpSession session = request.getSession();//从session池中去找,如果有,直接返回,没有,创建一个新的返回;
HttpSession session = request.getSession(true);//从session池中去找,如果有,直接返回,没有,创建一个新的返回;
HttpSession session = request.getSession(false);//从session池中去找,如果有,直接返回,没有,返回null
除此之外,如果你访问的是一个jsp资源,那么也会拥有session对象
2、作为域对象中的方法
方法 | 说明 |
---|---|
setAttribute(String name, Object obj); | 向域对象中设置值 |
getAttribute(String name); | 从域对象获取值 |
removeAttribute(String name); | 从域对象中删除值 |
范围:一次会话
3、session的API
4、生命周期
创建
- 当用户访问服务端时,首次碰到request.getSession()
销毁
- 服务器非正常关闭
- session超时(默认30分钟,可以配置)
- session销毁
注意
- 服务器正常关闭,session还是存在的
- 原因是:session对象不在内存中,被序列化到硬盘上,此时重新启动服务器,还是可以将session加载到内存中的
二、案例:一次性验证码校验
1、执行流程
2、代码实现
<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>登录页面</title>
<script type="text/javascript">
window.onload = function(){
document.getElementsByTagName("img")[0].onclick=function(){
//alert("abc");
this.src="VerifyCodeServlet?date="+new Date().getTime();
}
}
</script>
</head>
<body>
<form action="/web_day37/LoginServlet" method="post">
用户名:<input type="text" name="username" size="30px"/><br />
密 码:<input type="password" name="password" size="30px"/><br />
验证码:<input type="text" name="verifyCode" size="12px"/>
<img src="VerifyCodeServlet"><br>
<input type="submit" value="登录" />
</form>
</body>
</html>
import java.awt.image.BufferedImage;
import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import cn.itcast.vcode.utils.VerifyCode;
/**
* 生成验证码
*/
public class VerifyCodeServlet extends HttpServlet {
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
response.setContentType("text/html;charset=utf-8");
request.setCharacterEncoding("utf-8");
//1.创建一个VerifyCode对象
VerifyCode vc = new VerifyCode();
//2.获得验证码图片
BufferedImage image = vc.getImage();
//3.获得验证码图片中的文字内容
String text = vc.getText();
//4.将验证码文字内容保存到session域
request.getSession().setAttribute("vc", text);
//5.将验证码图片响应到指定位置
vc.output(image, response.getOutputStream());
}
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
doGet(request, response);
}
}
import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
/**
* 一次性验证码校验
*/
public class LoginServlet extends HttpServlet {
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
response.setContentType("text/html;charset=utf-8");
request.setCharacterEncoding("utf-8");
//1.获取用户输入的验证码数据
String verifyCode = request.getParameter("verifyCode");
//2.从session域中获得服务器生成验证数据
String vc = (String) request.getSession().getAttribute("vc");
//3.比对
if(verifyCode.equalsIgnoreCase(vc)){
//给出提示信息
response.getWriter().write("<h3 style='color:green'>您眼神真好!</h3>");
}else{
response.getWriter().write("<h3 style='color:red'>你瞎啊!</h3>");
}
}
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
doGet(request, response);
}
}
案例2:URL重写
session默认依赖cookie,如果浏览器可以禁用cookie,那么session就不能使用了么?
用户访问服务器不过就是通过超链接和表单而已!
如果每个请求都有一个名为jsessionid的参数的话,那么也可以不使用cookie
这种方式就是URL重写,但要求每个链接和每个表单都要URL重写
在每个页面中的每个链接和表单中都添加名为jSessionId的参数,值为当前sessionid
当用户点击链接或提交表单时也服务器可以通过获取jSessionId这个参数来得到客户端的sessionId,找到sessoin对象
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>URL重写</title>
</head>
<body>
<h1>URL重写:方式1</h1>
<a href="/web_day37/URLServlet;jsessionid=<%=session.getId() %>" >主页</a>
<form action="/web_day37/URLServlet;jsessionid=<%=session.getId() %>" method="post">
<input type="submit" value="提交"/>
</form>
</body>
</html>
使用response.encodeURL()对每个请求的URL处理,这个方法会自动追加jsessionid参数,与上面我们手动添加是一样的效果
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>URL重写</title>
</head>
<body>
<h1>URL重写方式2</h1>
<a href='<%=response.encodeURL("/web_day37/URLServlet") %>' >主页</a>
<form action='<%=response.encodeURL("/web_day37/URLServlet") %>' method="post">
<input type="submit" value="提交"/>
</form>
</body>
</html>
package com.itheima.web.servlet;
import java.io.IOException;
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 URLServlet extends HttpServlet {
private static final long serialVersionUID = 1L;
public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
// 处理post请求中文乱码问题
request.setCharacterEncoding("utf-8");
// 处理响应的中文乱码问题
response.setContentType("text/html;charset=utf-8");
// 获取session对象
HttpSession session = request.getSession();
// 获取sessionID
String id = session.getId();
response.getWriter().write(id);
}
public void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
doGet(request, response);
}
}
使用response.encodeURL()更加“智能”,它会判断客户端浏览器是否禁用了Cookie,如果禁用了,那么这个方法在URL后面追加jsessionid,否则不会追加