Cookie与Session简介

Cookie与Session简介

本章介绍重点:

本章重点为大家介绍在Web开发过程当中经常会使用到的Cookie与Session的概念,它们的使用方法和应用场景,以及它们的优点与局限等等。深刻理解与掌握它们的用法,可以更好的帮助我们开发出正确可用的产品。

 

 

我们为什么需要Cookie与Session:

在开始本章程的介绍之前,我们有必要要问自己一个问题,我们为什么需要Cookie与Session?它们可以帮助我们解决什么问题?

让我们先来了解了解我们经常使用的HTTP协议是什么:HTTP是一个属于应用层的面相对象的应用协议,它具有以下五个特点:

  • 支持客户端<->服务器服务
  • 简单快速
  • 灵活
  • 无连接
  • 无状态

如何理解HTTP的无状态特性?用当下流行的一句话来描述就是“人生若只如初见”。HTTP协议处理事务请求没有记忆能力,对同一个URL的请求没有上下文的关系,你所发出的每一次HTTP请求都是独立的,它的执行情况与响应的结果不会受到之前的HTTP请求的影响,当然它也不会干扰影响后续的HTTP请求与响应,处理HTTP请求的服务器没有保存客户端的状态

可以设想一下,假如基于这些特性而不做任何的特殊处理与改进,我们访问网络站点时会是怎样的体验?拿网购来说吧。当我们访问某电子商城的时候,提示需要输入用户名以及密码,我们按要求填写所需信息成功登陆,琳琅满目的商品展示在我们的眼前,我看上了一款最新的电子产品,打算点进去看看详细介绍,可接下的情况却让我们大跌眼镜,由于服务器没有我们的登陆状态,网站竟要求我重新输入用户名跟密码?这将会是一个多么糟糕的用户体验。

很明显,HTTP的这种无状态的特性严重的阻碍了我们与服务器的交互,于是两种用于保持HTTP连接状态的技术就应用而生了:Cookie与Session,这也是我们本章的介绍重点。

 

 

Cookie:

 Cookie是什么?

翻阅维基百科以及百度百科,我们不难发现,Cookie 是在 HTTP 协议下,服务器或脚本用以维护客户工作站信息的一种方式。它是由 Web 服务器保存在用户浏览器(客户端)上的小文本文件,可以用于记录用户的活动或者是与记录与状态相关的信息。Cookie是由W3C组织提出,最早由NetScape公司开发实现,现已经成为了一种标准,主流浏览器都支持Cookie机制。

Cookie的工作机制可以参见下面的图示:

正如前面所说,Cookie保存在客户端电脑,不同的浏览器,存放的路径可能有所不同,如下列举几个常见主流浏览器的存放位置:

  • IE存放位置:C:\Users\{$UserName}\AppData\Roaming\Microsoft\Windows\Cookies\xxx.txt
  • FireFox存放位置:C:\Users\{$UserName}\AppData\Roaming\Mozilla\Firefox\Profiles\{$xxx.default}\cookies.sqlite
  • Chrome存放位置:C:\Users\{$UserName}\AppData\Local\Google\Chrome\User Data\Default\Cookies

注意:IE浏览器中,IE将各个站点的Cookie分别保存为一个txt纯文本文件;而Firefox和Chrome是将所有的Cookie都保存在一个文件中,该文件的格式为SQLite3数据库格式的文件。

 

 Cookie的属性:

Cookie的常用属性可以参阅下列表格:

 

 Cookie的Server Side操作:

创建一个新的Cookie,我们可以通过以下的代码来实现:

protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
	Cookie myCookie = new Cookie("username", "WebOpenShare");
	myCookie.setMaxAge(300);
	myCookie.setDomain("www.webopenshare.com");
	myCookie.setPath("/");
	myCookie.setSecure(false);
	response.addCookie(myCookie);
}

运行上述的代码,我们便可以得到一个名为"username",其对应的值为"WepOpenShare"。(如果你是本地运行Tomcat服务器,请记得修改你电脑hosts文件)

 

Cookie对象没有提供直接修改其属性的方法,要修改原有Cookie的值,我们只能够通过创建同名的Cookie并添加到response中覆盖掉原Cookie的设置,如下所示:

protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
	// ...
	Cookie myModifiedCookie = new Cookie("username", "MyWebOpenShare");
	myModifiedCookie.setMaxAge(600);
	myModifiedCookie.setDomain("www.webopenshare.com");
	myModifiedCookie.setPath("/");
	myModifiedCookie.setSecure(false);
	response.addCookie(myModifiedCookie);
}

同样的,Cookie对象也没有提供直接删除某一个Cookie的操作方法,想要删除某一个Cookie,我们只能够通过新建一个maxAge为0的同名Cookie,把它添加到response中删除原先的Cookie,具体如下代码所示:

protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
	// ...
	Cookie deleted = new Cookie("username", "MyWebOpenShare");
	deleted.setMaxAge(0);
	deleted.setDomain("www.webopenshare.com");
	deleted.setPath("/");
	deleted.setSecure(false);
	response.addCookie(deleted);
}

注意:修改跟删除某一个Cookie时,我们要通过创建一个同名Cookie来进行覆盖,对于这一个同名Cookie,除了它的value跟maxAge属性可以不同,其余的所有属性必须跟要修改的Cookie保持一致,否则将会操作失败。

 

 Cookie的Client Side操作:

我们知道Cookie是保存在客户端的,那么我们可不可以通过一些脚本语言,例如JavaScript在浏览器中操作Cookie呢?如果有,我们可不可以像在Server Side操作Cookie一样,对Cookie进行读写/修改甚至是删除的操作呢?

可以肯定的是,我们可以通过脚本在浏览器中操作Cookie,但是出于安全性的考虑,它所允许的操作非常有限,仅限于读取当前域名下的Cookie,不可以修改或者删除Cookie。通过下面的代码我们就可以读取出当前Domain下的Cookies.

<script>document.write(document.cookie);</script>

 

 Cookie应该存放什么值:

前面的介绍当中,我们提及Cookie存放在客户端的文件上,如果客户端被入侵,那么这些Cookie文件存在被盗的潜在危险;另一方面,我们都知道,HTTP协议采用的是明文传输的方式,如果有人监听或者是截取了我们的请求,那么我们通过Cookie传送给服务器的信息就就全部曝露在入侵者面前。因此,存放在Cookie里面的值应当尽量避免个人敏感信息,如果非要存放敏感关键信息的时候,也要先经过加密处理之后再存放。

 

 

Session:

Session是什么?

Session是另外一种用户保持HTTP连接状态的解决方案,与Cookie不同,Session存放于服务器内存当中,服务器采用了一种类似于散列表(Hashtable)的形式来存放Session对象信息。

Session保存在服务器上,所以它会消耗服务器的资源,因此,我们不应该在Session里面存放太多太过复杂厚重的对象跟信息,在高并发的情况之下,这样做很容易会使得服务器内存溢出使得程序异常或者最终宕机。

Session的机制:

Session的机制,可以参见下图:

 

Session何时创建?

Session何时被创建呢?是不是我们访问服务器就会创建一个Session呢?答案是否定的,只有我们在程序中调用到Session的时候,服务器才会帮我们创建Session对象。例如在Servlet当中,当我们调用request.getSession()的方法时,服务器就会创建一个Session对象。但是细心的朋友可能会发现,当我访问某一个JSP页面的时候,也会有Session对象生成,此时我并没有在Servlet或者是JSP当中显式的使用任何的request.getSession()方法。这里我特别强调的是显式这个词语,其实当我们访问JSP的时候,JSP编译成Servlet的时候默认会帮我们添加这样的代码:HttpSession session = request.getSession(),这也是为什么我们可以什么都不做,就直接在JSP页面当中使用session.getAttribute()或者是其它的操作。

 

Session何时销毁?

前面谈了Session的创建,接下来我们来看看Session何时被销毁?当然,关闭服务器可以保证所有的Session被销毁。那关闭浏览器呢?很多人有一个误解,觉得只要我关闭了浏览器,Session就销毁了。其实这种理解是不全面的,我们知道,Session是由服务器创建并维护的,因此销毁与否须由服务器来完成,单纯关闭端浏览器并不会触发销毁内存的动作,如果我们重新打开浏览器,并向服务器发送之前的Session ID,是可以找回之前的Session的。只有在关闭浏览器的同时触发一条服务器请求,告诉服务器销毁掉内存,那才可以做到这样的效果。

恰恰是由于关闭浏览器并不能销毁内存,出于安全性的考量,我们需要为Session来设置一个有效期,当一次访问距离上次的请求超过这个有效期的话,那之前的Session就会销毁失效。

 

Cookie被禁用时?

Session的工作机制,默认情况下是需要浏览器的Cookie来配合工作的。当服务器创建一个全新的Session之后,会向浏览器发送一个Session ID的信息,通常是以Cookie的形式返回给客户端,在接下来的请求中,客户端便会自动在请求当中携带上这个Session ID的参数,服务器根据传递上来的Session ID直接从服务器中查找返回之前的Session对象。但是如果客户端禁用Cookie呢?

由于Cookie可以被人为的禁止,必须有其它机制以便在Cookie被禁止时仍然能够把Session ID传递回服务器。经常被使用的一种技术叫做URL重写,就是把Session ID直接附加在URL路径的后面,附加方式也有两种,一种是作为URL路径的附加信息,表现形式为http://${domain}:${port}/${uri};SESSIONID=xxxxxxxxxxx;另一种是作为查询字符串附加在URL后面,表现形式为http://${domain}:${port}/${uri}?SESSIONID=xxxxxxxxxxx

 

Session常用方法:

Session的常用方法总结如下表所示:

 

抛出引子:

部署在同一服务器上的所有应用之间是不是共享同一个Session?请关注我们,在后续章节跨应用Session共享中我们会为您揭秘。

 

我要小额赞助,鼓励作者写出更好的文章:

 

转载于:https://www.cnblogs.com/websharing/p/8487472.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值