HTTP 协议和状态保持

   HTTP 协议本身是无状态的,这和 HTTP 协议本来的目的是相符的,客户端只需要简单的向服务器请求下载某些文件,无论是客户端还是服务器都没有必要纪录彼此过去的行为,每一次请求之间都是独立的,好比一个顾客和一个自动售货机或一个普通的(非会员制)大卖场之间的关系相同。

  然而聪明(或贪心?)的人们非常快发现如果能够提供一些按需生成的动态信息会使 web 变得更加有用,就像给有线电视加上点播功能相同。这种需求一方面迫使 HTML 逐步添加了表单、脚本、 DOM 等客户端行为,另一方面在服务器端则出现了 CGI 规范以响应客户端的动态请求,作为传输载体的 HTTP 协议也添加了文件上载、 cookie 这些特性。其中 cookie 的作用就是为了解决 HTTP 协议无状态的缺陷所作出的努力。至于后来出现的 session 机制则是又一种在客户端和服务器之间保持状态的解决方案。

  让我们用几个例子来描述一下 cookie 和 session 机制之间的差别和联系 。笔者原来常去的一家咖啡店有喝 5 杯咖啡免费赠一杯咖啡的优惠,然而一次性消费 5 杯咖啡的机会微乎其微,这时就需要某种方式来纪录某位顾客的消费数量。想象一下其实也无外乎下面的几种方案:

   1 、该店的店员非常厉害,能记住每位顾客的消费数量,只要顾客一走进咖啡店,店员就知道该怎么对待了。这种做法就是协议本身支持状态。

   2 、发给顾客一张卡片,上面记录着消费的数量,一般更有个有效期限。每次消费时,如果顾客出示这张卡片,则此次消费就会和以前或以后的消费相联系起来。这种做法就是在客户端保持状态。

   3 、发给顾客一张会员卡,除了卡号之外什么信息也不纪录,每次消费时,如果顾客出示该卡片,则店员在店里的纪录本上找到这个卡号对应的纪录添加一些消费信息。这种做法就是在服务器端保持状态。

  由于 HTTP 协议是无状态的,而出于种种考虑也不希望使之成为有状态的,因此,后面两种方案就成为现实的选择。具体来说 cookie 机制采用的是在客户端保持状态的方案,而 session 机制采用的是在服务器端保持状态的方案。同时我们也看到,由于采用服务器端保持状态的方案在客户端也需要保存一个标识,所以 session 机制可能需要借助于 cookie 机制来达到保存标识的目的,但实际上他更有其他选择。

  理解 cookie 机制

   cookie 机制的基本原理就如上面的例子相同简单,不过更有几个问题需要解决: “ 会员卡 ” 怎么分发; “ 会员卡 ” 的内容;及客户怎么使用 “ 会员卡 ” 。

  正统的 cookie 分发是通过扩展 HTTP 协议来实现的,服务器通过在 HTTP 的响应头中加上一行特别的指示以提示浏览器按照指示生成相应的 cookie 。然而纯粹的客户端脚本如 JavaScript 或 VBScript 也能生成 cookie 。

  而 cookie 的使用是由浏览器按照一定的原则在后台自动发送给服务器的。浏览器检查所有存储的 cookie ,如果某个 cookie 所声明的作用范围大于等于将要请求的资源所在的位置,则把该 cookie 附在请求资源的 HTTP 请求头上发送给服务器。意思是麦当劳的会员卡只能在麦当劳的店里出示,如果某家分店还发行了自己的会员卡,那么进这家店的时候除了要出示麦当劳的会员卡,还要出示这家店的会员卡。

   cookie 的内容主要包括:名字,值,过期时间,路径和域。

  其中域能指定某一个域比如 .google.com ,相当于总店招牌,比如宝洁公司,也能指定一个域下的具体某台机器比如 www.google.com 或 froogle.google.com ,能用飘柔来做比。

  路径就是跟在 域名 后面的 URL 路径,比如 / 或 /foo 等等,能用某飘柔专柜做比。

  路径和域合在一起就构成了 cookie 的作用范围。

  如果不设置过期时间,则表示这个 cookie 的生命期为浏览器会话期间,只要关闭浏览器窗口, cookie 就消失了。这种生命期为浏览器会话期的 cookie 被称为会话 cookie 。会话 cookie 一般不存储在硬盘上而是保存在内存里,当然这种行为并不是规范规定的。如果设置了过期时间,浏览器就会把 cookie 保存到硬盘上,关闭后再次打开浏览器,这些 cookie 仍然有效直到超过设定的过期时间。

  存储在硬盘上的 cookie 能在不同的浏览器进程间共享,比如两个 IE 窗口。而对于保存在内存里的 cookie ,不同的浏览器有不同的处理方式。对于 IE ,在一个打开的窗口上按 Ctrl-N (或从文件菜单)打开的窗口能和原窗口共享,而使用其他方式新开的 IE 进程则不能共享已打开的窗口的内存 cookie ;对于 Mozilla Firefox0.8 ,所有的进程和标签页都能共享同样的 cookie 。一般来说是用 javascript 的 window.open 打开的窗口会和原窗口共享内存 cookie 。浏览器对于会话 cookie 的这种只认 cookie 不认人的处理方式经常给采用 session 机制的 web 应用程式研发者造成非常大的困扰。

  下面就是个 goolge 设置 cookie 的响应头的例子

HTTP/1.1 302 Found
Location: http://www.google.com/intl/zh-CN/
Set-Cookie: PREF=ID=0565f77e132de138:NW=1:TM=1098082649:LM=1098082649:S=KaeaCFPo49RiA_d8; expires=Sun, 17-Jan-2038 19:14:07 GMT; path=/; domain=.google.com
Content-Type: text/html

  这是使用 HTTPLook 这个 HTTP Sniffer 软件来俘获的 HTTP 通讯纪录的一部分

  浏览器在再次访问 goolge 的资源时自动向外发送 cookie

  使用 Firefox 能非常容易的观察现有的 cookie 的值

  使用 HTTPLook 配合 Firefox 能非常容易的理解 cookie 的工作原理。

   IE 也能设置在接受 cookie 前询问

  这是个询问接受 cookie 的对话框。

  理解 session 机制

  session 机制是一种服务器端的机制,服务器使用一种类似于散列表的结构(也可能就是使用散列表)来保存信息。

  当程式需要为某个客户端的请求创建一个 session 的时候,服务器首先检查这个客户端的请求里是否已包含了一个 session 标识   -   称为 session id ,如果已包含一个 session id 则说明以前已为此客户端创建过 session ,服务器就按照 session id 把这个 session 检索出来使用(如果检索不到,可能会新建一个),如果客户端请求不包含 session id ,则为此客户端创建一个 session 并且生成一个和此 session 相关联的 session id , session id 的值应该是个既不会重复,植蝗菀妆徽业焦媛梢苑略斓淖址 ??? 飧 ?ession id 将被在本次响应中返回给客户端保存。

  保存这个 session id 的方式能采用 cookie ,这样在交互过程中浏览器能自动的按照规则把这个标识发挥给服务器。一般这个 cookie 的名字都是类似于 SEEESIONID ,而。比如 weblogic 对于 web 应用程式生成的 cookie , JSESSIONID=ByOK3vjFD75aPnrF7C2HmdnV6QZcEbzWoWiBYEnLerjQ99zWpBng!-145788764 ,他的名字就是 JSESSIONID 。

  由于 cookie 能被人为的禁止,必须有其他机制以便在 cookie 被禁止时仍然能够把 session id 传递回服务器。经常被使用的一种技术叫做 URL 重写,就是把 session id 直接附加在 URL 路径的后面,附加方式也有两种,一种是作为 URL 路径的附加信息,表现形式为 http://...../xxx;jsessionid=ByOK ... 99zWpBng!-145788764 另一种是作为查询字符串附加在 URL 后面,表现形式为 http://...../xxx?jsessionid=ByOK ... 99zWpBng!-145788764
这两种方式对于用户来说是没有差别的,只是服务器在解析的时候处理的方式不同,采用第一种方式也有利于把 session id 的信息和正常程式参数区分开来。

  为了在整个交互过程中始终保持状态,就必须在每个客户端可能请求的路径后面都包含这个 session id 。

  另一种技术叫做表单隐藏字段。就是服务器会自动修改表单,添加一个隐藏字段,以便在表单提交时能够把 session id 传递回服务器。

  这种技术目前已较少应用,笔者接触过的非常古老的 iPlanet6(SunONE 应用服务器的前身 ) 就使用了这种技术。实际上这种技术能简单的用对 action 应用 URL 重写来代替。

  在谈论 session 机制的时候,常常听到这样一种误解 “ 只要关闭浏览器, session 就消失了 ” 。其实能想象一下会员卡的例子,除非顾客主动对店家提出销卡,否则店家绝对不会轻易删除顾客的资料。对 session 来说也是相同的,除非程式通知服务器删除一个 session ,否则服务器会一直保留,程式一般都是在用户做 log off 的时候发个指令去删除 session 。然而浏览器从来不会主动在关闭之前通知服务器他将要关闭,因此服务器根本不会有机会知道浏览器已关闭,之所以会有这种错觉,是大部分 session 机制都使用会话 cookie 来保存 session id ,而关闭浏览器后这个 session id 就消失了,再次连接服务器时也就无法找到原来的 session 。如果服务器设置的 cookie 被保存到硬盘上,或使用某种手段改写浏览器发出的 HTTP 请求头,把原来的 session id 发送给服务器,则再次打开浏览器仍然能够找到原来的 session 。

  恰恰是由于关闭浏览器不会导致 session 被删除,迫使服务器为 seesion 设置了一个失效时间,当距离客户端上一次使用 session 的时间超过这个失效时间时,服务器就能认为客户端已停止了活动,才会把 session 删除以节省存储空间。

cookie与session机制相关推荐

  1. 关于cookie的文章(cookie与session机制)

    会话(Session)跟踪是Web程序中常用的技术,用来跟踪用户的整个会话.常用的会话跟踪技术是Cookie与Session.Cookie通过在客户端记录信息确定用户身份,Session通过在服务器端 ...

  2. php session 机制,Cookie、Session机制详解及PHP中Session处理

    会话机制 Cookie/Session: 在web应用中,常用的会话追踪机制是Cookie和Session.而Cookie是通过在浏览器里记录确定用户身份,Session在服务器端记录信息确定用户身份 ...

  3. Cookie 和 Session机制具体解释

    原文地址:http://blog.csdn.net/fangaoxin/article/details/6952954     会话(Session)跟踪是Web程序中经常使用的技术.用来跟踪用户的整 ...

  4. cookie 和 session 机制

    cookie机制 Cookie实际上是Web服务端与客户端(典型的是浏览器)交互时彼此传递的一部分内容,内容可以是任意的,但要在允许的长度范围之内.客户端会将它保存在本地机器上(如IE便会保存在本地的 ...

  5. form组件、cookie、session机制

    一.django form组件 1.渲染标签 2.校验数据 3.展示信息 校验数据: 第一步需要一个form类 from django import formsclass MyForm(forms.F ...

  6. Servlet的Cookie和Session机制

    Servlet Cookies Cookies定义:Cookies是存储在客户端计算机上的文本文件,并保留了用户的各种跟踪信息. Cookies作用:会话保持,如完成用户的登录与状态保持 Cookie ...

  7. 基于Token的WEB后台登录认证机制(并讲解其他认证机制以及cookie和session机制)

    几种常用的认证机制 HTTP Basic Auth HTTP Basic Auth简单点说明就是每次请求API时都提供用户的username和password,简言之,Basic Auth是配合RES ...

  8. Cookie/Session机制详解--如何区分不同用户

    转载自:https://www.cnblogs.com/zhouhbing/p/4204132.ht 会话(Session)跟踪是Web程序中常用的技术,用来跟踪用户的整个会话.常用的会话跟踪技术是C ...

  9. [转]Cookie/Session机制详解

    会话(Session)跟踪是Web程序中常用的技术,用来跟踪用户的整个会话.常用的会话跟踪技术是Cookie与Session.Cookie通过在客户端记录信息确定用户身份,Session通过在服务器端 ...

最新文章

  1. ASP获取地址栏URL地址方法
  2. POJ 2387 Til the Cows Come Home
  3. xshell进行ssh链接报错“所选的用户密钥未在远程主机上注册”处理
  4. 产品经理和项目经理有哪些区别?
  5. 3.5 Bounding Box预测
  6. 《大话设计模式》第29章-OOTV杯超级模式大赛—模式总结(五)
  7. Wannafly挑战赛25 A 因子
  8. Linux 中 ext、ext2、ext3、ext4 文件系统介绍与区别
  9. 深度学习在视频动作识别应用
  10. (详细)华为荣耀8青春 PRA-AL00的usb调试模式在哪里开启的流程
  11. OpenGL鼠标移动方块
  12. 一键批量下载皮皮虾视频
  13. 绿色花灯【热门主题】
  14. 下载rpm离线安装包
  15. PTA 7-114 用if-else语句编程百分制成绩转换为五分制成绩
  16. Oracle分区表操作
  17. 基于树莓派实现AS608指纹识别
  18. 安卓平台的功耗一般分析
  19. 视频教程-全新大数据企业电商数据仓库项目实战教程-大数据
  20. python中true和false_我对python里True和False的理解

热门文章

  1. C++ | 内联函数
  2. 交通肇事罪定罪前批捕是否合法
  3. matlab zeros size标量,错误使用 zeros Size 输入必须为标量。
  4. 什么是redo log和undo log
  5. Java对象数组排序
  6. ferret 爬取动态网页
  7. ORA-00942: 表或视图不存在
  8. Java位运算的基础及使用(意义)
  9. 传统厂家如何开展社交电商+新零售+私域流量,附案例分析及搭建方法!
  10. 新传工作运用计算机吗,广播电视中计算机技术的运用