首先,HTTP协议是一种无状态的协议,也就是说web浏览器与服务器间不会建立一个长久的连接,对于事物处理没有记忆的能力,那么在使用过程中可能会一些不便。比如说打开淘宝的页面,不可能每添加一个商品就要输入一遍账号及密码。所以我们需要把状态信息存储起来以方便后面的使用【HTTP/1.1 引入 Cookie 来保存状态信息】
cookie和session都是用来保存状态信息的,都是保持客户端状态的机制,都是为解决HTTP无状态的问题做出的努力
产生过程
请求头Cookie:常用来表示请求者身份
响应头Set-Cookie:设置和页面相关联的cookie
服务端为每一个登录的客户端在服务器主机上创建一个session(会话),会话中描述客户端的信息,将session保存在数据库,通过Set-Cookie将session id【身份标识】以及重要信息返回给客户端,客户端将其保存在cookie文件中,下次请求服务端时直接从cookie文件读取信息,通过Cookie传递给服务端
服务器发送的响应报文包含 Set-Cookie 首部字段,客户端得到响应报文后把 Cookie 内容保存到浏览器中
客户端之后对同一个服务器发送请求时,会从浏览器中取出 Cookie 信息并通过 Cookie 请求首部字段发送给服务器。
Cookie
是服务器发送到用户浏览器并保存在本地的一小块数据,它会在浏览器之后向同一服务器再次发起请求时被携带上,用于告知服务端两个请求是否来自同一浏览器。由于之后每次请求都会需要携带 Cookie 数据,因此会带来额外的性能开销(尤其是在移动环境下)
Cookie 曾一度用于客户端数据的存储,因为当时并没有其它合适的存储办法而作为唯一的存储手段,但现在随着现代浏览器开始支持各种各样的存储方式,Cookie 渐渐被淘汰。新的浏览器 API 已经允许开发者直接将数据存储到本地,如使用 Web storage API(本地存储和话存储)或 IndexedDB
用途:
会话状态管理(如用户登录状态、购物车、游戏分数或其它需要记录的信息)
个性化设置(如用户自定义设置、主题等)
浏览器行为跟踪(如跟踪分析用户行为等)
记录用户ID、用户密码、用户浏览过的记录、但不会记录浏览器的设置
Cookie的理解:
- 不止一个
- 保存在客户端,按照在客户端中的存储位置分为内存Cookie、硬盘Cookie
- HTTP中Cookie明文传送、HTTPS中密文传送
- 有些Cookie在用户退出会话时删除,有效保护隐私
- cookie并不安全,别人会分析存在本地的cookie并进行cookie欺骗
- 单个cookie保存数据不能超过4k,且很多浏览器限制一个站点最多保存20个cookie
cookie和离线(本地存储)的区别?
- cookie会在浏览器和服务器之间来回传递,而本地存储只会在本地保存。
- cookie可以限制路径,数据大小也不能超过4kb,而本地存储的大得多,可以达到5M
- cookie在过期时间之前一直有效,本地存储始终有效
cookie的基本属性:
- domain:可以访问该cookie的域名,如为google.com,那么所有以此结尾的域名都可以访问
- path:cookie的使用路径,
- httponly:一旦设置,通过js脚本无法读取到cookie信息,可以有效防止XSS攻击,增加安全性
- secure:该cookie是否使用安全协议传输,如HTTPS就是安全的,在网络上传输数据前会为其加密
- expires:生存周期,默认是暂时存在的,即浏览器会话期间
怎么提高cookie的安全性
- 对保存在cookie中的敏感信息进行加密
- 设置httponly属性为true
- 设置secure属性为true
- 为cookie设置有效期
- 给cookie加个时间戳、IP戳,让cookie在同个IP下多久失效
Session
利用Session存储在服务器端,存储在服务器端的信息更加安全
Session 可以存储在服务器上的文件、数据库或者内存中。也可以将Session存储在Redis这种内存型数据库中,效率会更高
使用 Session 维护用户登录状态的过程如下:
用户进行登录时,用户提交包含用户名和密码的表单,放入 HTTP 请求报文中;
服务器验证该用户名和密码,如果正确则把用户信息存储到 Redis 中,它在 Redis 中的Key称为Session ID;
服务器返回的响应报文的Set-Cookie首部字段包含了这个Session ID,客户端收到响应报文之后将该Cookie值存入浏览器中;
客户端之后对同一个服务器进行请求时会包含该 Cookie 值,服务器收到之后提取出 Session ID,从 Redis 中取出用户信息,继续之前的业务操作
应该注意 Session ID 的安全性问题,不能让它被恶意攻击者轻易获取,那么就不能产生一个容易被猜到的 Session ID值。此外,还需要经常重新生成Session ID
在对安全性要求极高的场景下,例如转账等操作,除了使用Session管理用户状态之外,还需要对用户进行重新验证,比如重新输入密码,或者使用短信验证码等方式
session的理解
- session的生存周期默认是30分钟
- 保存在服务器上
- 当访问增多时比较占服务器的性能
Cookie与session:
- session是服务端为每一客户端单独创建的会话,保存在服务端
- Cookie是服务端通过Set-Cookie响应给客户端的信息,保存在客户端
- Cookie 只能存储 ASCII 码字符串,而 Session 则可以存储任何类型的数据,因此在考虑数据复杂性时首选Session
- Cookie 存储在浏览器中,容易被恶意查看。如果非要将一些隐私数据存在Cookie中,可以将Cookie值进行加密,然后在服务器进行解密
- 对于大型网站,如果用户所有的信息都存储在 Session 中,那么开销是非常大的,不建议将所有的用户信息都存储到 Session 中
即使禁用了cookie,session机制也不会失效
浏览器禁用 Cookie,无法使用 Cookie 来保存用户信息,只能使用Session。除此之外,不能再将Session ID存放到Cookie中,而是使用URL重写技术,将Session ID作为URL的参数进行传递