cookie是什么?

cookie是一种最原始也最简单的客户端存储方式,是存储在浏览器中的纯文本。举例来说, 一个 Web 站点可能会为每一个访问者产生一个唯一的ID, 然后以 Cookie 文件的形式保存在每个用户的机器上。浏览器的安装目录下会专门有一个 cookie 文件夹来存放各个域下设置的cookie。如果使用浏览器访问 Web, 会看到所有保存在硬盘上的 Cookie。在这个文件夹里每一个文件都是一个由“名/值”对组成的文本文件,另外还有一个文件保存有所有对应的 Web 站点的信息。在这里的每个 Cookie 文件都是一个简单而又普通的文本文件。透过文件名, 就可以看到是哪个 Web 站点在机器上放置了Cookie(当然站点信息在文件里也有保存)。

什么样的数据适合存储在cookie中

存储在cookie中的数据,每次都会被浏览器自动放在http请求中,如果这些数据并不是每个请求都需要发给服务端的数据,浏览器这设置自动处理无疑增加了网络开销;但如果这些数据是每个请求都需要发给服务端的数据(比如身份认证信息),浏览器这设置自动处理就大大免去了重复添加操作。所以对于那设置“每次请求都要携带的信息(最典型的就是身份认证信息)”就特别适合放在cookie中,其他类型的数据就不适合了。

cookie 的属性选项

每个cookie都有一定的属性,如什么时候失效,要发送到哪个域名,哪个路径等等。这些属性是通过cookie选项来设置的,cookie选项包括:expires、domain、path、secure、HttpOnly。在设置任一个cookie时都可以设置相关的这些属性,当然也可以不设置,这时会使用这些属性的默认值。在设置这些属性时,属性之间由一个分号和一个空格隔开。

  • expires

expires 是 http/1.0协议中的选项,在新的http/1.1协议中expires已经由 max-age 选项代替,两者的作用都是限制cookie 的有效时间。expires的值是一个时间点(cookie失效时刻= expires),expires必须是 GMT 格式的时间。可以通过new Date().toGMTString()或者 new Date().toUTCString() 来获得。对于失效的cookie浏览器会清空。如果没有设置该选项,则默认有效期为session,即会话cookie。这种cookie在浏览器关闭后就没有了。而max-age 的值是一个以秒为单位时间段(cookie失效时刻= 创建时刻+ max-age)。另外,max-age 的默认值是 -1(即有效期为 session );若max-age有三种可能值:负数、0、正数。负数:有效期session;0:删除cookie;正数:有效期为创建时刻+ max-age。

  • domain 和 path

domain是域名,path是路径,两者加起来就构成了 URL,domain和path一起来限制 cookie 能被哪些 URL 访问。

一句话概括:某cookie的 domain为“baidu.com”, path为“/ ”,若请求的URL(URL 可以是js/html/img/css资源请求,但不包括 XHR 请求)的域名是“baidu.com”或其子域如“api.baidu.com”、“dev.api.baidu.com”,且 URL 的路径是“/ ”或子路径“/home”、“/home/login”,则浏览器会将此 cookie 添加到该请求的 cookie 头部中。

domain和path2个选项共同决定了cookie何时被浏览器自动添加到请求头部中发送出去。如果没有设置这两个选项,则会使用默认值。domain的默认值为设置该cookie的网页所在的域名,path默认值为设置该cookie的网页所在的目录。

特别说明1:
发生跨域xhr请求时,即使请求URL的域名和路径都满足 cookie 的 domain 和 path,默认情况下cookie也不会自动被添加到请求头部中。若想知道原因请阅读本文最后一节)

特别说明2:
domain是可以设置为页面本身的域名(本域),或页面本身域名的父域,但不能是公共后缀 public suffix。举例说明下:如果页面域名为 www.baidu.com, domain可以设置为“www.baidu.com”,也可以设置为“baidu.com”,但不能设置为“.com”或“com”。

  • secure

secure选项用来设置cookie只在确保安全的请求中才会发送。当请求是HTTPS或者其他安全协议时,包含 secure 选项的 cookie才能被发送至服务器。默认情况下,cookie不会设置secure选项(即为空),不管是HTTPS协议还是HTTP协议的请求,cookie 都会被发送至服务端。但要注意一点,secure选项只是限定了在安全情况下才可以传输给服务端,但并不代表你不能看到这个 cookie。

如果想在客户端即网页中通过 js 去设置secure类型的 cookie,必须保证网页是https协议的。在http协议的网页中是无法设置secure类型cookie的。

  • httpOnly

这个选项用来设置cookie是否能通过 js 去访问。默认情况下,cookie不会带httpOnly选项(即为空),客户端是可以通过js代码去访问(包括读取、修改、删除等)这个cookie的。当cookie带httpOnly选项时,客户端则无法通过js代码去访问(包括读取、修改、删除等)这个cookie。在客户端是不能通过js代码去设置一个httpOnly类型的cookie的,这种类型的cookie只能通过服务端来设置。

从上面介绍中,大家是否会有这样的疑问:为什么我们要限制客户端去访问cookie?其实这样做是为了保障安全。

试想:如果任何 cookie 都能被客户端通过document.cookie获取会发生什么可怕的事情。当我们的网页遭受了 XSS 攻击,有一段恶意的script脚本插到了网页中。这段script脚本做的事情是:通过document.cookie读取了用户身份验证相关的 cookie,并将这些 cookie 发送到了攻击者的服务器。攻击者轻而易举就拿到了用户身份验证信息,于是就可以摇摇大摆地冒充此用户访问你的服务器了(因为攻击者有合法的用户身份验证信息,所以会通过你服务器的验证)。

如何设置 cookie?

cookie既可以由服务端来设置,也可以由客户端来设置。

  • 服务端设置 cookie

服务端可以设置cookie 的所有选项。不管你是请求一个资源文件(如 html/js/css/图片),还是发送一个ajax请求,服务端都会返回response。而response header中有一项叫set-cookie,是服务端专门用来设置cookie的。不能将多个cookie放在一个set-cookie字段中,set-cookie字段的值就是普通的字符串。一个set-Cookie字段只能设置一个cookie,当你要想设置多个 cookie,需要添加同样多的set-Cookie字段。

  • 客户端设置 cookie

在网页即客户端中我们也可以通过js代码来设置cookie。客户端可以设置cookie 的expires、domain、path、secure(条件:只有在https协议的网页中,客户端设置secure类型的 cookie 才能成功),但无法设置HttpOnly选项。当要用 js 设置多个cookie时,要重复执行document.cookie = "key=name"。

如下:

document.cookie = "name=Jonh";
document.cookie = "age=12";
document.cookie = "class=111";

如何修改、删除

  • 修改 cookie

要想修改一个cookie,只需要重新赋值就行,旧的值会被新的值覆盖。但要注意一点,在设置新cookie时,path/domain这几个选项一定要旧cookie 保持一样。否则不会修改旧值,而是添加了一个新的 cookie。

  • 删除 cookie

删除一个cookie 也挺简单,也是重新赋值,只要将这个新cookie的expires 选项设置为一个过去的时间点就行了。但同样要注意,path/domain/这几个选项一定要旧cookie 保持一样。

总结

  • 什么时候 cookie 会被覆盖:name/domain/path 这3个字段都相同的时候;
  • 关于domain的补充说明(参考1/参考2):如果显式设置了 domain,则设置成什么,浏览器就存成什么;但如果没有显式设置,则浏览器会自动取 url 的 host 作为 domain 值;新的规范中,显式设置 domain 时,如果 value 最前面带点,则浏览器处理时会将这个点去掉,所以最后浏览器存的就是没有点的(注意:但目前大多数浏览器并未全部这么实现)
  • 前面带点‘.’和不带点‘.’有啥区别:带点:任何 subdomain 都可以访问,包括父 domain;不带点:只有完全一样的域名才能访问,subdomain 不能(但在 IE 下比较特殊,它支持 subdomain 访问)
  • cookie都是保存在客户端的,服务器通过request获得都是客户端的数据
  • 以下是对一些方法的解释
  1. Cookie[] getCookies()返回一个数组,包含客户端发送该请求的所有的 Cookie 对象。

  2. Object getAttribute(String name)以对象形式返回已命名属性的值,如果没有给定名称的属性存在,则返回 null。

  3. String getHeader(String name)以字符串形式返回指定的请求头的值。Cookie也是头的一种;

  4. String getParameter(String name)以字符串形式返回请求参数的值,或者如果参数不存在则返回 null。

因此request.getHeader和request.getCookies方法可以取到http请求中的cookie值

了解Cookie是什么相关推荐

  1. HTTP 协议入门 — (TCP/IP协议族、通信传输流、URI 与 URL 的区别、Cookie 状态管理、HTTP 支持的方法、状态码类别、HTTP 首部字段)

    TCP/IP协议族 在介绍 HTTP 协议之前,我们先对 TCP/IP 协议族有个大概的了解,TCP/IP 协议从上到下主要分为应用层.传输层.网络层和数据链路层,各层的主要功能如下表所示: 协议层 ...

  2. cookie 免密登录_python

    我们都知道 HTTP 是无状态的,用户每次打开 web 页面时,服务器都打开新的会话,而且服务器也不会自动维护客户的上下文信息,那么服务器是怎么识别用户的呢? 这就是本文今天要讲解的内容.当服务端需要 ...

  3. 你想了解的Cookie和Session就在这~

    目录 1.会话的概念 2.保存会话的两种技术 3.Cookie 4.Session(重点) 1.会话的概念 我们知道session的意思就是会话,Cookie和Session 是两种会话技术,我们首先 ...

  4. Cookie和Session的区别与联系

    Cookie和Session Session 会话的理解 Session的作用 HTTP协议的无状态特点 Session的实现原理(重点) Session常用方法: Cookie 基本介绍 经典案例 ...

  5. java爬取验证码图片_JAVA HttpClient实现页面信息抓取(获取图片验证码并传入cookie实现信息获取)...

    JAVA HttpClient实现页面信息抓取(获取图片验证码并传入cookie实现信息获取) 发布时间:2018-05-18 16:41, 浏览次数:632 , 标签: JAVA HttpClien ...

  6. cookie用法之一,最简单cookie操作

    一.先引用封装好的JS<script src="https://img.huiyiguanjia.com/cdnfile/public/publicfunction.js"& ...

  7. redis缓存和cookie实现Session共享

    分布式项目中要实现单点登录(SSO - Single Sign On):对于同一个客户端(例如 Chrome 浏览器),只要登录了一个子站(例如 a.com),则所有子站(b.com.c.com)都认 ...

  8. 关于cookie与本地 存储的区别的问题。

    1. cookie在浏览器和服务器间来回传递.而sessionStorage和localStorage不会自动把数据发给服务器,仅在本地保存. 2. cookie数据还有路径(path)的概念,可以限 ...

  9. 不同级域名中的 Cookie 共享

    HTTP 响应头中 Set-Cookie 行未指定 domain 时则设置访问的域名 seliote.com 可以设置 seliote.com(也可以写成 .seliote.com 意思一样) 与 w ...

  10. 手动添加Cookie

    Controller设置Cookie第一种方式: 写:Response.SetCookie(new HttpCookie("mycookie"){ Value="1234 ...

最新文章

  1. 优雅的缓存解决方案--设置过期时间
  2. 利用DNS Zone Transfers漏洞工具dnswalk
  3. spacevim 添加自动折行
  4. 编程方法学笔记:karel
  5. SQL Server里的 ISNULL 与 Oracle 中的 NULLIF
  6. Unity 碰撞器和触发器的理解
  7. 阿里确认研发车载小程序 这些功能太方便了!
  8. (转)UIButton用法详解一
  9. 【SpringBoot_ANNOTATIONS】组件注册 03 FilterType
  10. 二级 c语言真题及答案,3月计算机二级C语言真题及答案(完整版)
  11. 诺基亚10.22变革影响的分析
  12. http接口 Spring boot中的Http压缩配置gzip
  13. html鼠标悬停闪烁,鼠标悬停闪烁星星插件jQuery-canvas-sparkles
  14. Linux环境变量PSI指什么,psi是什么单位?
  15. python_多点拟合曲线并计算曲率半径
  16. c3p0 签出超时:resourcepool.TimeoutException: A client timed out while waiting to acquire a resource
  17. js获取当前日期之后四个月的日期
  18. java判断一天是星期几_java判断今天星期几
  19. 原 RPCA以及LRR
  20. count(*) 和 count(1) 有什么区别?哪个性能最好?

热门文章

  1. 教我如何使用python编写一个界面
  2. MySQL 两张表关联更新(用一个表的数据更新另一个表的数据)两个表使用条件从另外一个表获取数据更新本表
  3. Git如何删除自己创建的项目
  4. 如何在一个小时内加密你的全部数字生活?
  5. OCR识别软件(uTools)→{个人笔记记录}
  6. parameterType、parameterMap与resultMap
  7. Unable to publish SessionDestroyedEvent for session (未解决)
  8. Android6.0以上应用在长时间在后台,因为内存不足导致系统回收内存,当再次启动应用出现Fragment重叠或者空白、异常解决方案(提供模拟内存不足导致系统回收内存的方案)。
  9. 什么是国际物流专线?国际快递专线又是什么呢?
  10. quickBI数据脱敏