Cookie和Session
HTTP协议本身是无状态的。什么是无状态呢,即服务器无法判断用户身份和行为
cookie实际上是一小段的文本信息。客户端请求服务器,如果服务器需要记录该用户状态,就使用response向客户端浏览器颁发一个Cookie, 户端会把Cookie保存起来。 当浏览器再次请求该网站时,浏览器把请求的网址连同该Cookie一同提交给服务器。服务器检查该Cookie,以此来辨认用户状态。
Cookie的构成
在Set-Cookie中设置需要向客户端发送的cookie,cookie格式如下:
Set-Cookie: "name=value;domain=.domain.com;path=/;expires=Sat, 11 Jun 2019 11:29:42 GMT;HttpOnly;secure"
其中 name=value 是必选项,其它都是可选项。Cookie的主要构成如下:
name:一个唯一确定的cookie名称。通常来讲cookie的名称是不区分大小写的。
value:存储在cookie中的字符串值。**最好为cookie的name和value进行url编码**
domain:cookie对于哪个域是有效的。所有向该域发送的请求中都会包含这个cookie信息。这个值可以包含子域(如:e.baidu.com),也可以不包含它(如:.baidu.com,则对于baidu.com的所有子域都有效)。
path: 表示这个cookie影响到的路径,浏览器跟会根据这项配置,像指定域中匹配的路径发送cookie。
expires:失效时间,表示cookie何时应该被删除的时间戳(也就是,何时应该停止向服务器发送这个cookie)。如果不设置这个时间戳,浏览器会在页面关闭时即将删除所有cookie;不过也可以自己设置删除时间。这个值是GMT时间格式。**如果客户端和服务器端时间不一致,使用expires就会存在偏差。并且如果给cookie设置一个过去的时间,浏览器会立即删除该cookie**
max-age:与expires作用相同,用来告诉浏览器此cookie多久过期(单位是秒),而不是一个固定的时间点。正常情况下,max-age的优先级高于expires。
HttpOnly: 告知浏览器不允许通过脚本`document.cookie`去更改这个值,同样这个值在document.cookie中也不可见。但在http请求张仍然会携带这个cookie。注意这个值虽然在脚本中不可获取,但仍然在浏览器安装目录中以文件形式存在。这项设置通常在服务器端设置。
secure: 安全标志,指定后,只有在使用SSL链接时候才能发送到服务器,如果是http链接则不会传递该信息。
Cookie的不可跨域名性:
很多网站都会使用Cookie,不同浏览器采用不同的方式保存Cookie,而且每个网站的Cookie只能够被对应的网站使用。意思就是说当浏览器访问baidu时,只会带baidu的Cookie,而不会带其他网站的Cookie,这就是Cookie的不可跨域名性 。 Cookie在客户端是由浏览器来管理的。浏览器可以保证各个网站只能操作各个网站的Cookie,从而保证用户的隐私安全。
cookie的特点
如果要修改某个Cookie,只需要新建一个同名的Cookie,添加到response中覆盖原来的Cookie,
并将maxAge设置为0,并添加到response中覆盖原来的Cookie。注意是0而不是负数。负数代表其他的意义。 0表示立即删除该Cookie,max-Age属性为正数,则表示该Cookie会在maxAge秒之后自动失效。当max-Age属性为负数,则表示该Cookie只是一个临时Cookie,不会被持久化,仅在本浏览器窗口或者本窗口打开的子窗口中有效,关闭浏览器后该Cookie立即失效。
注意:修改、删除Cookie时,新建的Cookie除value、maxAge之外的所有属性,例如name、path、domain等,都要与原Cookie完全一样。否则,浏览器将视为两个不同的Cookie不予覆盖,导致修改、删除失败。
cookie的用途
(1)保存用户登录状态
例如将用户 id 存储于一个 cookie 内,这样当用户下次访问该页面 时就不需要重新登录了,现在很多论坛和社区都提供这样的功能。
cookie 还可以设置过期时间,当超过时间期限后,cookie 就会自动消失。因此,系统往往可以提示用户保持登录状态的时间:常见选项有一个月、三个 月、一年等。
(2)跟踪用户行为
例如一个天气预报网站,能够根据用户选择的地区显示当地的天气情况。 如果每次都需要选择所在地是繁琐的,当利用了 cookie 后就会显得很人性化了,系统能够记住上一次访问的地区,当下次再打开该页面时,它就会自动显示上次用户所在地区 的天气情况。
因为一切都是在后台完成,所以这样的页面就像为某个用户所定制的一样,使用起来非常方便定制页面。如果网站提供了换肤或更换布局的功能,那么可以使用 cookie 来记录用户的选项,例如:背景色、分辨率等。当用户下次访问时,仍然可以保存上一次访问的界面风格。
Session是什么
Session是另一种记录客户状态的机制,不同的是Cookie保存在客户端浏览器中,而Session保存在服务器上。客户端浏览器访问服务器的时候,服务器把客户端信息以某种形式记录在服务器上。这就是Session。客户端浏览器再次访问时只需要从该Session中查找该客户的状态就可以了。
每个用户访问服务器都会建立一个session,那服务器是怎么标识用户的唯一身份呢?事实上,用户与服务器建立连接的同时,服务器会自动为其分配一个SessionId。Session的实现需要依赖于Cookie,当服务端创建Session后,会返回一个JSESSIONID存到Cookie中,下次再请求时,请求头中携带的Cookie会将JSESSIONID一并带回到服务端,这样服务端就可以找到对应的Session对象。
Session
举个例子:
session从字面上讲,就是会话。这个就类似于你和一个人交谈,你怎么知道当前和你交谈的是张三而不是李四呢?对方肯定有某种特征(长相、身高等等)表明他就是张三。session也是类似的道理,服务器要知道当前发请求给自己的是谁。- 为了做这种区分,服务器就要给每个客户端分配不同的“身份标识”,这个身份表示也就是我们平常所说的
sessionId。然后客户端每次向服务器发请求的时候,都带上这个“身份标识”,服务器就知道这个请求来自于谁了。 - 至于客户端怎么保存这个“身份标识”,可以有很多种方式,对于浏览器客户端,大部分情况下都默认采用
cookie的方式,当然也可以使用localStorage和sessionStorage存储这个身份标识,大家可以依据自身需求进行使用。 - 需要注意的是,
session为一个会话,当页面不同即使是同一页面打开两次,也被视为同一次会话。 - 服务器使用
session把用户的信息临时保存在了服务器上,用户离开网站后session会被销毁。 - 这种用户信息存储方式相对
cookie来说更安全,但是session有一个缺陷:如果web服务器做了负载均衡,那么下一个操作请求到了另一台服务器的时候session会丢失。
综上所述,对session做个总结:
- 当程序需要为某个客户端的请求创建一个
session时,服务器首先检查这个客户端的请求里是否已包含了一个session标识( 称为sessionId),如果已包含则说明以前已经为此客户端创建过session,服务器就按照此sessionId把其对应的session检索出来使用(检索不到,会新建一个);反之,如果客户端请求不包含sessionId,则为客户端创建一个session并且生成一个与此session相关联的sessionId,sessionId的值应该是一个既不会重复,又不容易被找到规律以仿造的字符串,这个sessionId将被在本次响应中返回给客户端保存。保存这个sessionId的方式可以采用cookie,也可以是locaStorage和sessionStorage,这样在交互过程中浏览器可以自动的按照规则把这个标识发送给服务器。
Session与Cookie的区别
- Session存储数据在服务器端,Cookie在客户端
- Session没有数据大小限制,Cookie有
- Session数据安全,Cookie相对于不安全
LocalStorage本地存储 和 sessionStorage临时存储
-
sessionStorage 和 sessionStorage 是 HTML5 新增的两个特性,这两个特性主要是用来作为会话存储和本地存储来使用的,解决了 cookie 存储空间不足的问题;
-
sessionStorage 属性允许你访问一个 session Storage 对象,用于存储当前会话的数据, 存储在sessionStorage 里面的数据在页面会话结束时会被清除。页面会话在浏览器打开期间一直保持,并且重新加载或恢复页面仍会保持原来的页面会话。
-
localStorage 属性允许你访问一个 Document 源(origin)的对象 Storage 用于存储当前源的数据,除非用户人为清除(调用 localStorage api 或则清除浏览器数据), 否则存储在 localStorage 的数据将被长期保留。
图解
总结
相同点
- 存储大小一般均为5M左右
- 都有同源策略限制,跨域无法访问
- 数据仅在客户端中保进行存储,并不参与和服务器的通信(不会随着 http 请求发送到服务器)
- 以 key 和 value 的形式进行存储数据, value 值必须为字符串,不为字符串会自动转型( value 如果是对象则需要转为 json 进行存储)
不同点
生命周期
- localStorage 存储的数据是永久性的,除非用户人为删除否则会一直存在(调用 localStorage api 或则清除浏览器数据)。
- sessionStorage 存储的数据在当前会话结束时会被清除,一旦窗口或者标签页被关闭,那么所有通过 sessionStorage 存储的数据也会被删除。
作用域
- localStorage: 在同一个浏览器内,同源文档之间共享 localStorage 数据,可以互相读取、覆盖、清除(同浏览器限制、同源限制)
- sessionStorage: 与 localStorage 一样需要同一浏览器同源文档这一条件。除此之外 sessionStorage 的作用域还被限定在了窗口中,也就是说,只有同一浏览器、同一窗口的同源文档才能共享数据(同浏览器限制、同源限制、同标签页限制)