会话技术: 当用户打开浏览器的时候,访问不同的资源,知道用户将浏览器关闭,可以认为这是一次会话。
作用:因为 http 协议是一个无状态的协议,它记录不论上次访问的内容。用户在访问过程中难免会产生一些数据,通过会话技术就可以将起保存起来。
例如:用户登录、验证码、购物车、访问记录......
分类:
cookie:浏览器端会话技术
session:服务器端会话技术
cookie 是由服务器生成,通过 response 将 cookie 写回浏览器(set-cookie),保留在浏览器上,下一次访问,浏览器根据一定的规则携带不同的 cookie(通过request的头 cookie),我们服务器就可以接受 cookie。
cookie的api:new Cookie(String key,String value)setMaxAge(int 秒数);持久化若int为0;删除此cookie(前提必须路径一致)setPath(String path):设置cookie的路径若访问的链接的路径中包含cookie的path,则携带写回浏览器:response.addCookie(Cookie c)获取cookie:Cookie[] request.getCookies()cookie的常用方法:getName():获取cookie的key(名称)getValue:获取指定cookie的值
查看浏览器的 cookie:在 chrome 浏览器中,f12 打开调试工具,找到 Console 栏(或快捷键 Ctrl+Shift+j
打开 Console 栏),输入document.cookie()
查看。
1.创建一个serlvet RemServlet 路径:/rem2.在servlet中:获取指定cookie 例如:名称为 lastTimerequest.getCookies()判断cookie是否为空若为空:提示信息 第一次访问若不为空:获取此cookie的value展示信息:你上次访问时间是....将这次访问时间记录,写回浏览器
代码:
/*** 记录上次访问时间*/public class RemServlet extends HttpServlet {private static final long serialVersionUID = 1L;protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {//0.设置编码response.setContentType("text/html;charset=utf-8");PrintWriter w = response.getWriter();//1.获取指定名称的cookieCookie c=getCookieByName("lastTime",request.getCookies());//2.判断cookie是否为空if(c == null){//cookie为空 提示 第一次访问w.print("您是第一次访问!");}else{//cookie不为空 获取value 展示 上一次访问的时间String value = c.getValue();// lastTime=12312324234long time = Long.parseLong(value);Date date = new Date(time);w.print("您上次访问时间:"+date.toLocaleString());}//3.将当前访问时间记录//3.1创建cookiec=new Cookie("lastTime",new Date().getTime()+"");//持久化cookiec.setMaxAge(3600);//设置路径c.setPath(request.getContextPath()+"/");// /day11///3.2写回浏览器response.addCookie(c);}/*** 通过名称在cookie数组获取指定的cookie* @param name cookie名称* @param cookies cookie数组* @return*/private Cookie getCookieByName(String name, Cookie[] cookies) {if(cookies!=null){for (Cookie c : cookies) {//通过名称获取if(name.equals(c.getName())){//返回return c;}}}return null;}protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {doGet(request, response);}}
cookie 总结:
常用方法:setMaxAge(int 秒):设置cookie在浏览器端存活时间 以秒为单位若设置成 0:删除该cookie(前提必须路径一致)setPath(String path):设置cookie的路径.当我们访问的路径中包含此cookie的path,则携带默认路径:访问serlvet的路径,从"/项目名称"开始,到最后一个"/"结束例如:访问的serlvet路径: /day11/a/b/hello默认路径为: /day11/a/b手动设置路径: 以"/项目名"开始,以"/"结尾;
需求:当用户访问一个商品的时候,需要将该商品保留在浏览记录中。
步骤分析:
1.先将product_list.htm转成jsp2.点击一个商品,展示该商品的信息,将该商品id记录到cookie (GetProductById)获取之前的浏览记录 例如名称:ids判断cookie是否为空若为空 将当前商品的id起个名称 ids 放入cookie中 ids=1若不为空,获取值 例如:ids=2-1 当前访问的id=1 使用"-"分割商品id判断之前记录中有无该商品若有:将当前的id放入前面 结果 ids=1-2若没有:继续判断长度是否>=3若>=3,移除最后一个,将当前的id放入最前面若<3,直接将当前的id放入最前面.若 ids=3-2-1 现在访问1 结果 ids=1-3-2若 ids=4-3-2 现在访问1 结果 ids=1-4-33.再次回到product_list.jsp页面,需要将之前访问商品展示在浏览记录中获取ids 例如:ids=2-3-1切割
技术分析:cookie.setMaxAge(0)
步骤分析:
1.在浏览器记录中添加一个超链接<a href="/day1101/clearHistroy">清空</a>2.创建servlet clearHistroy创建一个cookie名称路径保持一致setMaxAge(0)写回浏览器3.页面跳转重定向 product_list.jsp
注意:
cookie不能跨浏览器
cookie中不支持中文
服务器端的会话技术。
浏览器访问服务器的时候,服务器会获取 jsessionid:
若获取到:要拿着这个 jsessionid 去服务器中(session池)查找有无此 session
若查找到了:拿过来直接使用,将该 session 的 jsessionid 通过响应返回给浏览器
若查找不到:创建一个session,将你的数据保存到这个session中,将当前 session 的 jsessionid 返回给浏览器
若获取不到:创建一个session,将你的数据保存到这个 session 中,将当前 session 的 jsessionid 返回给浏览器
对 session 的理解:
客户到银行办存蓄卡。客户相当于浏览器,存储卡的卡 ID 相当于 jsessionid,银行相当于服务器,服务器响应给浏览器“存储卡ID”(session 底层依赖 cookie)。
详细参考网上文章:Session机制、持久化、session="false"属性不创建session、显示创建session及其销毁
需求:在商品详情页面有一个添加到购物车,点击则将该商品添加到购物车,点击购物车链接将里面的所有商品展示出来。
技术分析:session
获取一个 session:request.getSession()
jsp页面上增加 <%@ page session="false"%> 才会让你自己 getSession(true)或 getSession()时创建session1、request.getSession() 等价于 request.getSession(true)这两个方法的作用是相同的,查找请求中是否有关联的jsessionid,如果有则返回这个号码所对应的session对象,如果没有则生成一个新的session对象。所以说,通过此方法是一定可以获得一个session对象。2、request.getSession(false) 查找请求中是否有关联的jsessionid号,如果有则返回这个号码所对应的session对象,如果没有则返回一个null。3、在JSP页面中有一个session的隐士对象,这个隐士对象是怎么产生的呢?我们大家都知道JSP页面最终要被转换成一个Java源文件,实际上这个隐士对象就是通过request.getSession(true)这个方法获得的,所以总是可以获得session对象的。如果设置了<%@ page session=false%>指令,容器不会调用以上方法,而并不是说以上方法不会返回session对象。
session域对象:xxxAttribute
生命周期:
创建:java 程序中第一次使用 request.getsession()
方法的时候创建
销毁:
①服务器非正常关闭②session超时默认时间超时:30分钟 web.xml有配置手动设置超时:setMaxInactiveInterval(int 秒)③手动干掉session★session.invalidate()
其他域对象:
ServletContext:共享的数据
HttpServletRequest:一次请求的数据
HttpSession:私有的数据
步骤分析:
1.点击添加到购物车的时候,提交到一个servlet add2CartServlet需要将商品名称携带过去2.add2CartServlet中的操作获取商品的名称将商品添加到购物车 购物车的结构 Map<String 名称,Integer 购买数量>将购物车放入session中就可以了将商品添加到购物车分析:获取购物车判断购物车是否为空若为空:第一次添加创建一个购物车将当前商品put进去.数量:1将购物车放入session中若不为空:继续判断购物车中是否有该商品若有:取出count 将数量+1将商品再次放入购物车中若没有:将当前商品put进去 数量:1提示信息:你的xx已添加到购物车中3.点击购物车连接的时候 cart.jsp从session获取购物车判断购物车是否为空若为空:提示信息若不为空:遍历购物车即可
代码:
/*** 添加到购物车*/public class Add2CartServlet extends HttpServlet {private static final long serialVersionUID = 1L;protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {//0.设置编码response.setContentType("text/html;charset=utf-8");PrintWriter w = response.getWriter();//1.获取商品的名称String name=request.getParameter("name");name=new String(name.getBytes("iso8859-1"),"utf-8");//2.将商品添加到购物车//2.1 从session中获取购物车Map<String,Integer> map=(Map<String, Integer>) request.getSession().getAttribute("cart");Integer count=null;//2.2判断购物车是否为空if(map==null){//第一次购物 创建购物车map=new HashMap<>();//将购物车放入session中grequest.getSession().setAttribute("cart", map);count=1;}else{//购物车不为空 继续判断购物车中是否有该商品count = map.get(name);if(count==null){//购物车中没有该商品count=1;}else{//购物车中有该商品count++;}}//将商品放入购物车中map.put(name, count);//3.提示信息w.print("已经将<b>"+name+"</b>添加到购物车中<hr>");w.print("<a href='"+request.getContextPath()+"/product_list.jsp'>继续购物</a> ");w.print("<a href='"+request.getContextPath()+"/cart.jsp'>查看购物车</a> ");}protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {doGet(request, response);}}
思路1:将购物车移除思路2:将session干掉步骤分析:在cart.jsp上添加一个超链接 清空购物车<a href="/day1101/clearCart">清空购物车</a>在clearCart中需要调用session.invalidate()重定向到购物车页面