关于Cookie的那些事
之前做项目的时候发现需要使用cookie,可是由于时间紧也没来得及学,最近打算系统地学习一下,之前漏掉的知识,毕竟要学的东西还很多。在这打算先说说cookie,就当是学习笔记吧,希望对大家有所帮助。
在TW老师的耳濡目染下,我现在学东西一般都会先画思维导图,就是列出自己对这个知识点的一些疑问,然后带着问题去学习。
学习过程见目录
Cookie是什么
Cookie是服务器保存在浏览器的一小段文本信息,每个Cookie的大小一般不能超过4KB。浏览器每次向服务器发出请求,就会自动附上这段信息。
那么问题来了,它会保存哪些信息呢?这就是下一个问题了
它会保存哪些信息
- Cookie的名字
- Cookie的值
- 到期时间
- 所属域名(默认是当前域名)
- 生效路径(默认是当前路径)
为什么要有Cookie
我们知道HTTP协议是无状态的,对于一个浏览器发出的多次请求,Web服务器是无法区分是不是来源于同一个浏览器的。所以,需要额外的数据用于维护会话。 Cookie 正是这样的一段随HTTP请求一起被传递的额外数据。
比如当你第一次访问一个网站的时候一般都会有新手引导,可是再次访问的时候这个新手引导就不会出现了,那么浏览器是如何知道你是否是第一次访问这个网站呢,这就是cookie的用武之地了。
当你访问某个网站的时候该网站就会在你的电脑上写入它的cookie信息,当你下一次访问的时候它就会判断你本地有没有它的cookie,然后显示相应的页面。
它有什么特点
- cookie是http协议的一部分,随着http请求发送到服务端
- 是document的一个属性,document.cookie
- cookie是字符串,每个键值之间使用;空格分开的。设置cookie的时候以字符串拼接的方式就可以
- 有数量和大小的限制。一般每个域cookie的数量不超过50个,IE6以下最多20个,IE7之后最多50个,FF最多50个,safari和chrome没有限制。大小一般为4KB,容量很小
- 一个网站的所有页面公用一套cookie
- 有过期时间,默认为浏览器关闭时自动清除cookie,当然可以人为设定过期时间
- 没有封装好的方法来直接操作cookie,需要自己封装:设置,删除,获取的方法
有没有类似功能的技术
常见的例如Session,localStorage,IndexDB等,其实这里说类似功能是不准确的,因为它们之间还是存在很大区别的,暂且将它们列出来,后续再去研究它们之间的区别。
如何使用
前面简单介绍了cookie,知道这些是远远不够的,重点是要知道怎么使用它。
写Cookie
设置Cookie可以有两种方式,一是通过document.cookie,而是通过Set-Cookie设置,下面一一介绍。
document.cookie设置Cookie
在用document.cookie设置Cookie的时候要注意以下几点:
Cookie的值必须写成key=value的形式。注意,等号两边不能有空格
可以把下面这样一个字符串赋值给document.cookie:document.cookie = ‘name=tom’;
如果要一次存储多个名/值对,可以使用分号加空格(; )隔开,例如:document.cookie=”userId=828; userName=hulk”;
document.cookie一次只能写入一个Cookie,而且写入并不是覆盖,而是添加
例如以下代码:document.cookie = ‘name=tom’;
document.cookie = ‘sex=male’;
以上代码执行的结果是设置一个cookie,其中包含name=tom和sex=male,它是往同一个cookie中添加一条数据,而不是重新生成一个cookie,它等同于这条代码的执行结果:document.cookie = ‘name=tom;sex=male’;
Set-Cookie设置Cookie
这种方法是通过HTTP请求头来设置的
Web 服务器通过发送一个称为 Set-Cookie 的 HTTP 消息头来创建一个 cookie,Set-Cookie 消息头是一个字符串,其格式如下(中括号中的部分是可选的):
Set-Cookie: key=value[; expires=date][; domain=domain][; path=path][; secure]
当存在一个 cookie,并允许设置可选项,该 cookie 的值会在随后的每次请求中被发送至服务器,cookie 的值被存储在名为 Cookie 的 HTTP 消息头中。
通过 Set-Cookie 指定的可选项只会在浏览器端使用,而不会被发送至服务器端。发送至服务器的 cookie 的值与通过 Set-Cookie 指定的值完全一样,不会有进一步的解析或转码操作。
上面的头信息中,Set-Cookie字段是服务器写入浏览器的Cookie,一行一个。
Set-Cookie: cookie_name1=cookie_value1
Set-Cookie: cookie_name2=cookie_value2; expires=Sun, 16 Jul 3567 06:23:41 GMT
注:
expires是cookie的一个属性,用于指定Cookie过期时间。它的格式采用Date.toUTCString()的格式。
如果不设置该属性,或者设为null,Cookie只在当前会话(session)有效,浏览器窗口一旦关闭,当前Session结束,该Cookie就会被删除。
浏览器根据本地时间,决定Cookie是否过期,由于本地时间是不精确的,所以没有办法保证Cookie一定会在服务器指定的时间过期。
读Cookie
如果你是用document.cookie设置的cookie的话,也可以使用document.cookie来读取
假如设置了cookie值为:
document.cookie = ‘a=1’;
document.cookie = ‘b=2’;
那么当执行console.log(document.cookie)的时候就会输出’a=1;b=2;’
如果你是以下面这种方式设置的cookie,那么就得手动分割字符串获得各个属性值了。
document.cookie = ‘a=1;b=3’;
既然读写cookie都可以用document.cookie实现,那么读写之间有什么区别呢?
一次可以读出全部Cookie,但是只能写入一个Cookie;
与服务器与浏览器之间的Cookie通信格式有关。浏览器向服务器发送Cookie的时候,是一行将所有Cookie全部发送浏览器向服务器发送Cookie的时候,是一行将所有Cookie全部发送
服务器告诉浏览器需要储存Cookie的时候,则是分行指定
修改Cookie
如果原始的Cookie是用Set-Cookie设置的,改变上面这个cookie的值,就必须使用同样的Set-Cookie;
只要有一个属性不同,就会生成一个全新的Cookie,而不是替换掉原来那个Cookie
删除Cookie
删除一个Cookie的简便方法,就是设置expires属性等于0,或者等于一个过去的日期
或者需要设置 cookie 的值为 null,就可以删除相应的 cookie
Cookie的限制
开头提到cookie一般为4KB,其实浏览器对cookie是有限制的
不同浏览器对Cookie数量的限制,规定不一样。目前,Firefox是每个域名最多设置50个Cookie,而Safari和Chrome没有域名数量的限制。
所有Cookie的累加长度限制为4KB。超过这个长度的Cookie,将被忽略,不会被设置
这个限制可能会导致很多操作无法正常实现,那么如何解决呢?
看到有人提到使用如下办法:
设置一个Cookie,但是这个Cookie内部使用&符号,设置了多部分的内容。
因此,读取这个Cookie的时候,就要自行解析,得到多个键值对。这样就规避了cookie的数量限制。
以上便是我对cookie基础的介绍,如需了解更多敬请期待我后续的文章,谢谢!
参考资料:
http://javascript.ruanyifeng.com/bom/cookie.html
http://www.cnblogs.com/xiaochaohuashengmi/archive/2010/06/13/1757658.html
http://www.crystalxue.com/2016/09/15/cookie/