javaWeb中cookie和session的区别与联系

一、cookie

1.诞生

  • Cookie是1993年由网景公司(Netscape)前雇员发明的一种进行网络会话状态跟踪的技术
  • 会话是由一组请求状态组成,请求与响应之间一定需要有数据传递,由此需要进行会话状态跟踪。然而HTTP协议是无状态协议,在不同的请求间是无法进行数据传递的。此时就需要一种可以进行请求间数据传递的会话跟踪技术,Cookie就是一种这样的技术

2.简介

  • Cookie是由服务器生成,保存在客户端的一种信息载体。这个载体中存放着用户访问该站点的会话状态信息(一般清空浏览器缓存会删除这些信息)。只要Cookie没有被清空,或者Cookie没有失效,那么,保存在其中的会话状态就有效
  • 用户在提交第一次请求后,由服务器生成Cookie,并将其封装到响应头中,以响应的形式发送给客户端。客户端接收到这个响应后,将Cookie保存到客户端。当客户端再次发送同类请求后,在请求中会携带保存在客户端的Cookie数据,发送到服务端,由服务器对会话进行跟踪

3.创建与添加

// 创建Cookie,key-value存储
Cookie cookie1 = new Cookie("username", "tom");
Cookie cookie2 = new Cookie("pwd", "123");
// 向响应头中添加Cookie
response.addCookie(cookie1);
response.addCookie(cookie2);

4.cookie属性设置

// 创建Cookie,key-value存储
Cookie cookie = new Cookie("username", "tom");
//生存时间,单位 秒
cookie.setMaxAge(10);
// 表示 该cookie的作用域,只有该path以及 其子路径 才能访问到 该cookie.  注意:这里指定的路径要求必须要添加上项目名称
cookie.setPath(req.getContextPath()+"/");

5.删除与修改cookie

// 没有删除, 修改,只有覆盖
// 创建一个 和 需要修改的 cookie name相同的cookie对象, 并放入响应对象中
Cookie cookie = new Cookie("username", "tom");
response.addCookie(cookie);
// 通过 创建一个 和 需要修改的 cookie name相同的cookie对象, 并设置生存时间为0(相当于删除),并放入响应对象中
Cookie cookie = new Cookie("username", "");
cookie.setMaxAge(0);//相当于删除
response.addCookie(cookie);

//设置Cookie的有效期。这个值为一个整型值,单位为秒
//该值大于0,表示将Cookie存放到客户端的硬盘
//该值小于0,与不设置效果相同,会将Cookie存放到浏览器的缓存
//该值等于0,表示Cookie一生成,马上失效
cookie.setMaxAge(60 * 60 * 24 * 10);    //设置Cookie的有效期为10天(例如登录页面上有10天内免登录字样)

6.查看cookie

  • 从请求中获取携带的cookie
// 获取请求中的cookie
Cookie[] cookies = request.getCookies();
if(null != cookies){
    //遍历cookies
  	for(Cookie cookie : cookies){
    	System.out.println(cookie.getName()+"="+cookie.getValue());
  	}
}

7.cookie特性

  • 只能保存客户端,但产生是在服务器端
  • 只能保存字符串,使用的字符集是ISO-8859-1
  • cookie可以被禁用,禁用后cookie失效
  • 安全性较低
  • 浏览器保存的cookie的数据有大小限制
    • 和浏览器有关
    • 一般在4k左右

二、session

1.简介

  • Session,即会话,是Web开发中的一种会话状态跟踪技术。当然所描述的Cookie也是一种会话跟踪技术。不同的是Cookie是将会话状态保存在了客户端,而Session则是将会话状态保存在了服务器端
  • 那么,到底什么是“会话”?当用户打开浏览器,从发出第一次请求开始,一直到最终关闭浏览器,就表示一次会话的完成

2.对Session域属性空间的操作

  • Session是一个专门用于存放数据的集合,我们一般称这个用于存放数据的内存空间为域属性空间,简称域。HttpSession中具有三个方法,是专门用于对该域属性空间中数据进行写、读操作的。
  • public void setAttribute(String name,Object value)该方法用于向Session的域属性空间中放入指定名称、指定值的域属性
  • public Object getAttribute(String name)该方法用于从Session的域属性空间中读取指定名称为域属性值
  • public void removeAttribute(String name)该方法用于从Session的域属性空间中删除指定名称的域属性(可以用于注销某个用户账号)

3.获取session

  • request.getSession()相当于request.getSession(true)

  • request.getSession(boolean flag)根据参数不同:

    • 参数为true

      浏览器发送请求到服务器,服务器会根据请求检查其中是否包含JSessionID,有JSessionID服务器会根据JSessionID查找对应的session对象,没有找到,创建并返回一个新的session对象

    • 参数为false

      浏览器发送请求到服务器,服务器会根据请求检查其中是否包含JSessionID,有JSessionID服务器会根据JSessionID查找对应的session对象,没有找到,返回null

4.session原理(重要)

① 写入Session列表:

  • 服务器对当前应用中的Session是以Map的形式进行管理的,这个Map称为Session列表。该Mapkey为一个32位长度的随机串,这个随机串称为JSessionID,value则为Session对象的引用
  • 当用户第一次提交请求时,服务端Servlet中执行到request.getSession()方法后,会自动生成一个Map.Entry对象,key为一个根据某种算法新生成的JSessionID,value则为新创建的HttpSession对象

在这里插入图片描述

在这里插入图片描述

② 服务器生成并发送Cookie

  • 在将Session信息写入Session列表后,系统还会自动将“JSessionID”作为name,这个32为长度的随机串作为value,以Cookie的形式存放到响应头中,并随着响应,将该Cookie发送到客户端

在这里插入图片描述

③ 客户端接收并发送Cookie

  • 客户端接收到这个Cookie后会将其存放到浏览器的缓存中。即,只要客户端浏览器不关闭,浏览器缓存中的Cookie就不会消失
  • 当用户提交第二次请求时,会将缓存中的这个Cookie,伴随着请求的头部信息,一块发送到服务器

④ 从Session列表中查找

  • 服务端从请求中读取到客户端发送来的Cookie,并根据Cookie的JSessionID的值,从Map中查找相应key所对应的value,即Session对象。然后,对该Session对象的域属性进行读写操作

在这里插入图片描述

以我的理解大概来讲就是:

  • 当用户第一次访问一个具有getSession(true)代码时,服务器会在session列表中自动创建一个Key(指的是32位长度的随机字符串)-Value(创建的HttpSession对象:session)键值对
  • 然后将JSessionID作为key和上面生成的32位长度的随机字符串作为value形成key-value键值作为参数保存到Cookie对象中(这里原来的32位长度的随机字符串key变成了现在的value)
  • 客户端再次发起同类请求会带上缓存中的cookie,服务器接收到请求来的cookie,将其JSessionIDvalue值与session列表匹配(实际上JSessionID的value值与session列表里其中的一个32位长度的随机字符串的key是同一个东西),找到相应的session引用,就可以进行session域的读写

5.session生存时间

  • 默认情况下,生存时间为30分钟。(从最后一次请求开始计算,30分钟后session会过期)
// 可以通过设置 生存时间,改变原始值
session.setMaxInactiveInterval(10);// 参数单位是 秒, 此处表示生存时间为10秒
// 一般不会刻意的修改该值

6.url重写

  • cookie禁用时,浏览器不保存JSessionID,所以浏览器发送请求时,其中没有携带JSessionID,服务器无法获取session,只能创建新的session返回给浏览器,但浏览器依然没有保存。通过在请求地址后加上 ;jsessionid=EA219D35E18BC9BA1C2B9506BF498ADA 后面的值是当时返回给浏览器的session的id(即JSessionID)。可以手动的让请求携带JSessionID,这样服务器就可以获取其对应的session。

  • 上面的操作太麻烦,所以提供了url重写的方法。

// 会自动的在url后拼接当前的JSessionID
<%
  // 在传入的url后拼接JSessionID,如果不需要拼接,则返回原始url
  String url1 = response.encodeURL(request.getContextPath()+"/jsp/t6.jsp");//一般转发时使用此方法
  // 在传入的url后拼接JSessionID,如果不需要拼接,则返回原始url
  String url2 = response.encodeRedirectURL("t6.jsp");// 一般重定向时使用此方法
%>
<a href="<%=url1 %>" >t6.jsp========11</a>
<a href="<%=url2 %>" >t6.jsp========22</a>
  • 禁用cookie更不安全,jsessionid会暴露在地址栏中
  • 一般cookie被禁用时,不做处理,只提示用户,将无法使用部分功能

参考资料

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章