JavaWeb详解(第二篇)之Servlet基础简介-会话技术介绍
Posted 穆瑾轩
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了JavaWeb详解(第二篇)之Servlet基础简介-会话技术介绍相关的知识,希望对你有一定的参考价值。
JavaWeb详解(第二篇)之Servlet基础简介-会话技术介绍
1、会话技术介绍
1.1、会话技术概述
1.1.1、什么是会话
会话是指:用户开一个浏览器,访问一个网站,只要不关闭该浏览器,不管该用户点击多少个超链接,访问多少资源,直到用户关闭浏览器,整个这个过程我们称为一次会话。
为什么我们要使用会话技术?
这里先科普下另外两个知识点HTTP 协议的五个特点:
1)简单快速;2)灵活;3)无连接;4)无状态;5)支持B/S及C/S模式。
1.1.2、什么是无连接
无连接:是限制每次连接只处理一个请求。服务器处理完客户的请求,并收到客户的应答后,即断开连接。采用这种方式可以节省传输时间。
我们知道在HTTP/1.0中默认使用短连接。也就是说,客户端和服务器每进行一次HTTP操作,就建立一次连接,任务结束就中断连接。早期这么做的原因是因为每个客户端(即浏览器)与服务器之间交换数据的间歇性较大,如果应用程序或者上层协议一直不发送数据,或者隔很长时间才发送一次数据,大部分通道实际上会很空闲,无端占用资源。因此HTTP的设计者有意利用这个特点将协议设计为请求时建立连接、请求完释放连接,以尽快将资源释放出来服务其他客户端,这样做的好处是,可以极大的减轻服务端的压力。
但随着时间的推移,网页变得越来越复杂。通常一个网页可能会有很多组成部分,除了文本内容,还会有诸如:js、css、图片等静态资源。如果每遇到这样一个Web资源,浏览器就会重新建立一个TCP连接,再发起HTTP请求,然后关闭,这就显得很低效。后来keep-alive被提出来解决低效率的问题。
从HTTP/1.1起,默认使用长连接(默认启用Keep-Alive),当一个网页打开完成后,客户端和服务器之间用于传输HTTP数据的TCP连接不会关闭,客户端再次访问这个服务器时,会继续使用这一条已经建立的连接。Keep-Alive不会永久保持连接,一般HTTP协议中keep-alive的连接复用机制主要是由服务端来控制的。
1.1.3、什么是无状态
无状态:是指协议对于事务处理没有记忆能力。缺少状态意味着如果后续处理需要前面的信息,则它必须重传,这样可能导致每次连接传送的数据量增大。但是服务器不需要先前信息时它的应答就较快。
HTTP在设计之初就没有考虑过要保存会话状态。无论你之前访问过什么网页、提交过什么数据,你获得的网页都是一样的;不同的浏览器访问同一个网页所得到的结果也是完全一样的。这就是所谓的“无状态”——访问URI得到的结果与上下文操作无关、与用户无关。
1.1.4、为什么使用会话技术
前面我们了解到HTTP并不会保存会话状态,也不关心整个上下文操作。面对日益复杂化的web应用,页面与页面、页面与用户之间难免产生点什么关系。
比如案例一:A和B两人在某购物网站上登陆账号后,想要知道A/B的偏好,A通过Servlet_Look,点开了一个详情链接是一个雷蛇鼠标,而B也通过Servlet_Look,点开了一个详情链接是一个机械键盘,这些信息都会被保存下来,但是这个Servlet_Look并不知道是谁在查看。现在,如果想要把这些信息保存下来呢?
思考下:能不能用我们之前学过的 HttpServletRequest 对象和 ServletContext 对象来保存这些数据呢?
答案是:不能。
不能用 HttpServletRequest 的原因:我们的一次会话中,存在多次请求和响应,而浏览器客户端的每一次请求都会产生一个 HttpServletRequest 对象,它只会保存此次请求的信息。之前保存的信息就会丢失。
不能用 ServletContext 的原因:ServletContext对象是被整个web应用所共享的,将数据都存到这里,无疑会无法区分具体信息的归属。是A浏览的、还是B浏览的?
比如案例二:A在自己电脑上,通过IE浏览器,请求Servlet_Login进入了购物网站登陆页面,并且成功登陆了。第二天,A又在自己电脑上通过IE浏览器请求Servlet_Login,此时服务器并不在知道是谁发起了这个HTTP请求,业务HTTP请求并不会标识是谁发起的。于是呢,A又要再次输一遍用户名和密码。
那鉴于这种情况,服务器怎么去保存这个信息呢?如果要绑定客户端、绑定用户这确实很麻烦了,如果是其他人使用呢?如果换了客户端呢?
于是,会话跟踪技术应运而生,一个是cookie 一个是session。会话跟踪技术可以解决我们很多问题。
1.2、Cookie技术
1.2.1、什么是Cookie
Cookie是由W3C组织提出,最早由netscape社区发展的一种机制。网页之间的交互是通过HTTP协议传输数据的,而Http协议是无状态的协议。服务器也无法确定用户信息,于是,W3C就提出了:给每一个用户都发一个通行证,无论谁访问的时候都需要携带通行证,这样服务器就可以从通行证上确认用户的信息。通行证就是Cookie(一般一个cookie大小限制4k)。
Cookie是客户端技术,服务器把每个用户的数据以cookie的形式写给用户各自的浏览器。当用户使用浏览器再去访问服务器中的web资源时,浏览器会把请求的网址连同Cookie一同交给服务器。这样,web资源处理的就是用户各自的数据了。
1.2.2、Cookie常用API
方法 | 说明 |
---|---|
response.addCookie(Cookie cookie) | 将Cookie添加到客户端 |
Cookie cookies[]=request.getCookies(); | 读取Cookie |
Cookie(String name, String value) | 构造一个cookie包含指定名称和值 |
getValue() | 返回cookie的值 |
setValue(String newValue) | 将新值赋给一个cookie之后创建的cookie |
setMaxAge(int expiry) | 设置cookie的生命周期,以秒为单位指定 |
getPath() | 返回这个cookie在服务器路径 |
setPath(String uri) | 指定一个路径对客户机cookie应该返回cookie |
getDomain() | 返回这个cookie设置的域名 |
getName() | 返回cookie的名称 |
1.2.3、创建和读取Cookie
使用案例:
import java.io.IOException;
import java.io.PrintWriter;
import javax.servlet.ServletException;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
public class CookieServletDemo1 extends HttpServlet{
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
response.setContentType("text/html;charset=gbk");
PrintWriter out = response.getWriter();
//创建Cookie
Cookie cookie=new Cookie("name","穆瑾轩");
//设置cookie的生命周期:MaxAge为正数,浏览器会把Cookie写到硬盘中
//MaxAge为负数,Cookie是临时性的,仅在本浏览器内有效,关闭浏览器Cookie就失效了
//如果MaxAge为0,则表示删除该Cookie
cookie.setMaxAge(3600);
//把cookie信息回写给浏览器
response.addCookie(cookie);
out.println("<form action='/CookieServletDemo1' method='post' >");
out.println("<input type='submit' value='创建Cookie' /><br />");
out.println("</form><br />");
out.flush();
out.close();
}
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
response.setContentType("text/html;charset=gbk");
//读取cookie信息
Cookie cookies[]=request.getCookies();
PrintWriter out = response.getWriter();
for(int i=0;i<cookies.length;i++){
Cookie cookie=cookies[i];
out.println(cookie.getName()+"="+cookie.getValue());
out.println("生命周期:"+cookie.getMaxAge());
}
out.flush();
out.close();
}
}
案例效果:
google会把Cookie写到Cookies文件中。IE会单独生成一个文件,存相应的Cookie。如果存入的Cookie的key相同,则会覆盖。
1.2.4、Cookie的生命周期和有效路径
Cookie的生命周期可以通过cookie.setMaxAge(秒),如果不设置setMaxAge则该cookie的生命周期当浏览器关闭时,就消亡;
cookie.setMaxAge(秒):
正数,表示在指定的秒数后过期;
负数,表示浏览器一关,Cookie就会被删除(默认值是-1)。
0,表示马上删除Cookie。
Cookie的path属性可以有效的过滤哪些Cookie可以发送给服务器,哪些不发。
使用案例:
import java.io.IOException;
import java.io.PrintWriter;
import javax.servlet.ServletException;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
public class CookieServletDemo2 extends HttpServlet{
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
response.setContentType("text/html;charset=gbk");
PrintWriter out = response.getWriter();
//创建Cookie:第一次访问/CookieServletDemo2时才添加
Cookie cookie=new Cookie("name","穆瑾轩");
//设置cookie的生命周期
cookie.setMaxAge(3600);
//创建Cookie2:如果访问/CookieServletDemo3时才添加
Cookie cookie2=new Cookie("name2","穆瑾轩2");
//设置cookie2的生命周期
cookie2.setMaxAge(3600);
cookie2.setPath("/CookieServletDemo3");
//把cookie信息回写给浏览器
response.addCookie(cookie);
response.addCookie(cookie2);
out.println("<form action='/CookieServletDemo2' method='post' >");
out.println("<input type='submit' value='创建Cookie' /><br />");
out.println("</form><br />");
out.flush();
out.close();
}
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
response.setContentType("text/html;charset=gbk");
//读取cookie信息
Cookie cookies[]=request.getCookies();
PrintWriter out = response.getWriter();
for(int i=0;i<cookies.length;i++){
Cookie cookie=cookies[i];
out.println(cookie.getName()+"="+cookie.getValue());
out.println("生命周期:"+cookie.getMaxAge());
}
//创建Cookie3:如果访问/CookieServletDemo2时才添加
Cookie cookie3=new Cookie("name3","穆瑾轩3");
//设置cookie3的生命周期
cookie3.setMaxAge(3600);
cookie3.setPath("/CookieServletDemo2");
response.addCookie(cookie3);
out.flush();
out.close();
}
}
案例效果:
上述案例中:当我访问http://localhost:8080/CookieServletDemo2时cookie2并没有被添加。
1.2.5、Cookie的域名
我们在学习javascript的时候,JavaScript出于安全方面的考虑(因同源策略的限制),不允许跨域调用其他页面的对象。同样,Cookie的隐私安全机制决定Cookie也是不可跨域的。简单的理解就是,不同URL之间的Cookie对象是无法访问的。
我们访问网站,很多为了记忆便捷,于是有了域名的概念。域名最终会被翻译为对应的IP地址,首先查找的就是我们的hosts文件,如果没有才会去DNS域名系统中获取。
此案例执行前提:
1)在C:\\Windows\\System32\\drivers\\etc路径下找到:hosts文件
配置如下域名和IP的映射关系:
127.0.0.1 localhost
127.0.0.1 www.mjx.com
使用案例:
import java.io.IOException;
import java.io.PrintWriter;
import javax.servlet.ServletException;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
public class CookieServletDemo3 extends HttpServlet{
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
response.setContentType("text/html;charset=gbk");
PrintWriter out = response.getWriter();
//创建Cookie:第一次访问/CookieServletDemo2时才添加
Cookie cookie=new Cookie("name","穆瑾轩from_www.mjx.com");
//设置cookie的生命周期
cookie.setMaxAge(3600);
//把cookie信息回写给浏览器
response.addCookie(cookie);
out.println("<form action='/CookieServletDemo3' method='post' >");
out.println("<input type='submit' value='创建Cookie' /><br />");
out.println("</form><br />");
out.flush();
out.close();
}
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
response.setContentType("text/html;charset=gbk");
//读取cookie信息
Cookie cookies[]=request.getCookies();
PrintWriter out = response.getWriter();
for(int i=0;i<cookies.length;i++){
Cookie cookie=cookies[i];
out.println(cookie.getName()+"="+cookie.getValue());
out.println("生命周期:"+cookie.getMaxAge());
}
out.flush();
out.close();
}
}
案例效果:
我们看到Domain栏位正是我们的域名,并且不同的域名间的Cookie是不共享的。
1.3、session技术
1.3.1、什么是session
前面我了解到Cookie是客户端技术, Session是服务器端技术,是另一种记录浏览器状态的机制。利用这个技术,服务器在运行时可以为每一个用户的浏览器创建一个其独享的session对象,由于session为用户浏览器独享,所以用户在访问服务器的web资源时,可以把各自的数据放在各自的session中,当用户再去访问服务器中的其它web资源时,其它web资源再从用户各自的session中取出数据为用户服务。
为什么需要session?Session比Cookie使用方便,Session可以解决Cookie解决不了的事情,Session可以存储对象,Cookie只能存储字符串。可以把Session看做是一个容器类类似HashMap。
session可以用来做什么:网上商城中的购物车、保存登录用户的信息、防止用户非法登录到某个页面中等等。
1.3.2、session常用API
方法 | 描述 |
---|---|
long getCreationTime(); | 获取Session被创建时间 |
String getId(); | 获取Session的id |
long getLastAccessedTime(); | 返回Session最后活跃的时间 |
ServletContext getServletContext(); | 获取ServletContext对象 |
void setMaxInactiveInterval(int var1); | 设置Session超时时间 |
int getMaxInactiveInterval(); | 获取Session超时时间 |
Object getAttribute(String var1); | 获取Session属性 |
Enumeration getAttributeNames(); | 获取Session所有的属性名 |
void setAttribute(String var1, Object var2); | 设置Session属性 |
void removeAttribute(String var1); | 移除Session属性 |
void invalidate(); | 销毁该Session |
boolean isNew(); | 该Session是否为新的 |
1.3.3、创建/读取/删除Session
1)得到session:
HttpSession session=request.getSession();
注: session是存在服务器的内存中,一个用户浏览器,独享一个session域对象。此方法等效于request.getSession(true),获取session,如果没有则新创建一个session。当然那就还有request.getSession(false),去获取session,如果没有则不创建。
2)得到session的ID
session.getId()
sessionid是一个会话的key,浏览器第一次访问服务器会在服务器端生成一个session,有一个sessionid和它对应。tomcat生成的sessionid叫做jsessionid。
tomcat的ManagerBase类提供创建sessionid的方法: 随机数+时间+jvmid;
客户端只保存sessionid到cookie中,而不会保存session,session对象的属性保存在服务器的内存中。
2)向session添加属性
session.setAttribute(String name, Object val);
3)从session得到属性
String name=(String) session.getAttribute(String name);
4)从session删除属性
session.removeAttribute("username");
1.3.4、Session生命周期和有效期
session的默认生命周期是30分钟。
1)设置Session超时时间
a)方式一:在tomcat/conf/web.xml修改配置
<!--找到这个配置:默认30分钟,超时时间修改为20分钟-->
<session-config>
<session-timeout>20</session-timeout>
</session-config>
b)方式二:在单个web应用的web.xml下去新增配置上诉配置
c)方式三:在程序中单独设置:setMaxInactiveInterval(int var1);
正是为超时时长(单位秒);负数表示永不超时。
2)getMaxInactiveInterval();
获取Session的超时时间。
注:Session的超时时间是以最后访问时间到下此访问时的这个时间段。如果这个时间段超过了超时时间,Session就会从内存中移除。
3)invalidate();
让当前的Session会话马上超时无效。
注:超时无效,并不会删除Session的id,只是此Session对象无法获取Session的属性。
使用案例:
1)新建一个SessionDemo
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;
public class SessionDemo extends HttpServlet{
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
response.setContentType("text/html;charset=gbk");
PrintWriter out = response.getWriter();
out.println("<body>");
out.println("<iframe name='target' width='500' height='300' style='float: left;'></iframe>");
out.println("<div style='float: left;'>");
out.println("<ul style='list-style: none;'>");
out.println("<li><a href='/SessionDemo2?action=isNew' target='target'>Session的创建和获取(id号、是否为新创建)</a></li>");
out.println("<li><a href='/SessionDemo2?action=setAttribute' target='target'>Session域数据的存储</a></li>");
out.println("<li><a href='/SessionDemo2?action=getAttribute' target='target'>Session域数据的获取</a></li>");
out.println("<li>Session的存活</li>");
out.println("<li>");
out.println("<ul style='list-style: none;'>");
out.println("<li><a href='/SessionDemo2?action=getMaxInactiveInterval' target='target'>获取Session的超时数据</a></li>");
out.println("<li><a href='/SessionDemo2?action=defaultLife' target='target'>Session的默认超时及配置</a></li>");
out.println("<li><a href='/SessionDemo2?action=lifeNew' target='target'>Session3秒超时销毁</a></li>");
out.println("<li><a href='/SessionDemo2?deleteNow=isNew' target='target'>Session马上销毁</a></li>");
out.println("</ul>");
out.println("</li>");
out.println("</ul>");
out.println("</div>");
out.println("</body>");
out.flush();
out.close();
}
}
2)新建一个SessionDemo2,并配置好web.xml
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 SessionDemo2 extends HttpServlet{
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
String action = request.getParameter("action");
System.out.println(action);
doPost(request, response);
}
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
response.setContentType("text/html;charset=gbk");
if("isNew".equals(request.getParameter("action"))) {
// 创建和获取Session会话对象:等效于request.getSession(true)
HttpSession session = request.getSession();
// 判断 当前Session会话,是否是新创建出来的
boolean isNew = session.isNew();
// 获取Session会话的唯一标识 id:此id由服务器创建:随机数+时间+jvmid
String id = session.getId();
response.getWriter().write("得到的Session,它的id是:" + id + " <br /> ");
response.getWriter().write("这个Session是否是新创建的:" + isNew + " <br /> ");
}else if("getAttribute".equals(request.getParameter("action"))) {
Object attribute = request.getSession().getAttribute("key1");
response.getWriter().write("从Session中获取出key1的数据是:" + attribute);
}else if("setAttribute".equals(request.getParameter("action"))) {
request.getSession().setAttribute("key1", "value1");
response.getWriter().write("已经往Session中保存了数据");
}else if("deleteNow".equals(request.getParameter("action"))) {
// 先获取Session对象
HttpSession session = request.getSession();
// 让Session会话马上超时:超时并不会移除sessionid
session.invalidate();
response.getWriter().write("Session已经设置为超时(无效)");
}else if("defaultLife".equals(request.getParameter("action"))) {
// 获取了Session的默认超时时长
int maxInactiveInterval = request.getSession().getMaxInactiveInterval();
response.getWriter().write("Session的默认超时时长为:" + maxInactiveInterval + " 秒 ");
}else if("lifeNew".equals(request.getParameter("action"))) {
// 先获取Session对象
HttpSession session = request.getSession();
// 设置当前Session3秒后超时
session.setMaxInactiveInterval(3);
response.getWriter().write("当前Session已经设置为3秒后超时");
}else if("getMaxInactiveInterval".equals(request.getParameter("action"))) {
// 先获取Session对象
HttpSession session = request.getSession();
response.getWriter().write("当前Session的超时时间是:"+session.getMaxInactiveInterval());
}
}
}
案例效果:
更换浏览器,同样能获得一个的sessionid。为什么服务器能够为不同的浏览器提供不同session?
因为每个浏览器去访问web站点的时候,如果发出的http请求头没有带JSESSIONID头就会自动给你创建一个并返回。
session技术底层其实是基于Cookie技术实现的。在没有当Cookie的情况下,发送请求,当request.getSession();创建了会话对象,服务器(Tomcat)就会创建一个Cookie对象,这个对象的key值是JSESSIONID。然后每次请求的时候,都会把sessionid以Cookie的形式发送给服务器。request.getSession();就会根据Cookie的id值找到之前创建好的session对象。
1.3.5、Session应用
1)登陆验证
HttpSession session=request.getSession();
User u=(User) session.getAttribute("user");
if(u==null){
request.setAttribute("error", "请输入用户名,密码登录");
//如果之前没有登陆,则转发到登陆页面
request.getRequestDispatcher("login.jsp").forward(request, response);
return;
}
2)验证码应用
第一步:新建一个login.jsp
<%@ page language="java" import="java.util.*" pageEncoding="GBK"%>
<!DOCTYPE html>
<html>
<head>
<title>login</title>
</head>
<body onload="changeCode('ImageServlet');">
<form action="/LoginServlet" method="post">
用户名: <input type="text" name="username"><br>
密码: <input type="password" name="password"><br>
验证码: <input type="text" name="checkcode">
<a href="javascript:changeCode('ImageServlet')"><img id="codeimg" style="width: 60px;height:20px;"><br></a>
<br> <input type="submit" value="登录">
</form>
</body>
<script type="text/javascript">
function changeCode(url){
window.document.getElementById("codeimg").src=url+"?"+Math.random();
}
</script>
</html>
第二步:新建一个LoginServlet
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;
public class LoginServlet extends HttpServlet{
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
request.getRequestDispatcher("login.jsp").forward(request, response);
}
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
response.setContentType("text/html;charset=GBK");
PrintWriter out = response.getWriter();
//获取用户的username和userpsw和验证码
String username=request.getParameter("username");
String userpsw=request.getParameter("userpsw");
String checkCode=request.getParameter("checkcode");
String checkCode2=(String) request.getSession().getAttribute("checkcode");
System.out.println(checkCode+"=="+checkCode2);
if(checkCode!=null && checkCode.toUpperCase().equals(checkCode2)){
response.getWriter().write("登陆成功!");
}
else{
request.getRequestDispatcher("login.jsp").forward(request, response);
if(checkCode==null) {
System.out.println("验证码为空!");
return;
}
request.setAttribute("err", "验证码有误");
System.out.println("验证码有误!");
}
out.flush();
out.close();
}
}
第三步:新建一个ImageServlet
import java.awt.Color;
import java.awt.Font;
import java.awt.Graphics;
import java.awt.image.BufferedImage;
import java.io.IOException;
import javax.imageio.ImageIO;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
public class ImageServlet extends HttpServlet{
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
// 7.禁止浏览器缓存随机图片
response.setDateHeader("Expires", -1);
response.setHeader("Cache-Control", "no-cache");
response.setHeader("Pragma", "no-cache");
// 6.通知客户机以图片方式打开发送过去的数据
response.setHeader("Content-Type", "image/jpeg");
// 1.在内存中创建一副图片
BufferedImage image = new BufferedImage(60, 30,
BufferedImage.TYPE_INT_RGB);
// 2.向图片上写数据
Graphics g = image.getGraphics();
// 设背景色
g.setColor(Color.BLACK);
g.fillRect(0, 0, 50, 20);
// 3.设置写入数据的颜色和字体
g.setColor(Color.RED);
g.setFont(new Font(null, Font.BOLD, 20));
// 4.向图片上写数据
String num = makeNum();
// 这句话就是把随机生成的数值,保存到session
request.getSession().setAttribute("checkcode", num);
System.out.println("当前验证码:"+num);
// 通过session就可以直接去到随即生成的验证码了
g.drawString(num, 0, 20);
// 5.把写好数据的图片输出给浏览器
ImageIO.write(image, "jpg", response.getOutputStream());
}
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
doGet(request, response);
}
// 该函数时随机生成7位数字
public String makeNum(){
String str = "0123456789ABCDEFGHIGKLMNOPQRSTUVWXYZ";
String s = "";
for (int i = 0; i < 4; i++){
int k = (int) (Math.random() * 36);
s = s + str.charAt(k);
}
return s;
}
}
案例效果:
1.3.6、总结cookie与session区别
1)存放位置
Cookie 存在客户端的临时文件夹;
Session 存放在服务器内存中,一个session 域对象为一个用户浏览器服务。
2)安全性
Cookie 是以明文方式存放在客户端,安全性弱,可以通过md5方式加密再存放;
Session 是存放在服务器内存中,所以安全性好。因为session 会占用服务器内存,因此不要向session存放过多过大的对象,会影响性能。
3)网络传送量
Cookie 会传递信息给服务器;
Session 的属性值不会给客户端。
4)生命周期
Cookie的生命周期是累计时间,比如:给cookie设置setMaxAge(30,30S后失效;
Session 的生命周期是间隔时间,比如:设置session 20min,在20min内,如果没有访问session,则session 失效。
以上是关于JavaWeb详解(第二篇)之Servlet基础简介-会话技术介绍的主要内容,如果未能解决你的问题,请参考以下文章