一.Cookie

1.什么是cookie?

Cookie 技术产生源于 HTTP 协议在互联网上的急速发展。随着互联网时代的策马奔腾,带宽等限制不存在了,人们需要更复杂的互联网交互活动,就必须同服务器保持活动状态(简称:保活)。

Cookie 是在 HTTP 协议下,服务器或脚本可以维护客户工作站上信息的一种方式。Cookie 是由 Web 服务器保存在用户浏览器(客户端)上的小文本文件,它可以包含有关用户的信息。无论何时用户链接到服务器,Web 站点都可以访问 Cookie 信息.

2.cookie的起源

Cookie最早是网景公司的前雇员Lou Montulli在1993年3月的发明。

3.Cookie时效性

Cookie的默认时效为Session,也就是说浏览器关闭,Cookie会和session一起失效,但是Cookie的有效时间是可以设置的。

Cookie有一个属性expires,设置其值为一个时间,那么当到达此时间后,此cookie失效。

实现如下:

//创建cookie实例。
HttpCookie cookie = new HttpCookie("id","666");
//设置cookie的过期时间,一小时后过期,自动清除文件
cookie.Expires = DateTime.Now.AddMonths(60);
//将创建的cookie文件输入到浏览器端
Response.Cookies.Add(cookie);
//读取cookie文件中存储的值
Response.Write(Request.Cookies["id"].Value);

4.Cookie文件的删除、销毁

由于 Cookie 在用户的计算机中,所以无法直接将其直接移除。所以我们用浏览器来删除 Cookie。首先是创建一个与要删除的 Cookie 同名的新 Cookie,将该 Cookie 的到期日期设置为早于当前日期的某个日期,当浏览器检查 Cookie 的到期日期时,浏览器便会丢弃这个现已过期的 Cookie。

//cookie的销毁,给他设置一个时间,他就被销毁了
cookie.Expires = DateTime.Now.AddMonths(-60); 

5.Cookie使用限制

Cookie是HTTP头中的一个字段,虽然HTTP本身对这个字段并没有多少限制,但是Cookie最终还是存储在浏览器里,所以不同的浏览器对Cookie的存储都有一些限制,不同的浏览器对 Cookie 的处理不一致,使用时一定要考虑。
客户端用户如果设置禁止 Cookie,则 Cookie 不能建立。 并且在客户端,一个浏览器能创建的 Cookie 数量根据浏览器的不同,其上限也不同。

6.执行流程:

1)、首先,客户端会发送一个http请求到服务器端。

2)、服务器端接受客户端请求后,发送一个http响应到客户端,这个响应头,其中就包含Set-Cookie头部,浏览器保存Cookie。

3)、浏览器第二次访问,将保存的cookie发给后台,后台识别并更新cookie,返回浏览器再次保存。

为了方便理解,可以先看下这张流程执行图加深概念

那么,在浏览器上面的请求头和Cookie在那?下图给大家截取了其中一种。

上面我们都是在tan浏览器上的Cookie,那么在Android开发中,我们该如何去管理和使用Cookie?

Okhttp作为经典到爆的网络框架,它的API(本文是基于Okhttp3.0版本以上,3.0以下的版本API有所不同)是通过OkhttpClient中的CookieJar或者拦截器去管理Cookie的。理论上,我们只需在构建单例OkhttpClient的时候,设置cookiejar或者拦截器,然后具体的操作(具体的操作也就是保存Cookie,取Cookie),Okhttp框架就会帮我们自动管理Cookie。

如下图:

这是其中一种通过集合的增查特性,就可以简单有效的帮我们管理Cookie。但我们还是要通过源代码去一探究竟。首先,CookieJar是一个接口。

英文注释翻译过来就是(对应段落翻译):

CookieJar这个接口为HTTP cookies提供了强大的支持和相关策略。

这种策略的实现作用会负责选择接受和拒绝那些cookie。一个合理的策略是拒绝所有的cookie,尽管这样会干扰需要cookie的基于会话的自身身份验证方案。

作为Cookie的持久性,该接口的实现也必须要提供Cookie的存储。一种简单的实现可以将cookie存储在内存中;复杂的系统可以使用文件系统用于保存已接受的cookie的数据库。这里的链接https://tools.ietf.org/html/rfc6265 指定cookie存储模型更新和过期的cookie的策略。

所以,Okhttp的源码告知我们可以将cookie存储在内存中;复杂的系统可以使用文件系统用于保存已接受的cookie的数据库。因此,我们就可以通过Map去简单的管理和使用。

继续分析CookieJar接口里面的方法,依旧上源码

里面有方法一个是saveFromResponse(HttpUrl url, List cookies)、loadForRequest(HttpUrl url)

saveFromResponse方法翻译:根据这个jar的方法,可以将cookie从一个HTTP响应保存到这里。

请注意,如果响应,此方法可能被称为第二次HTTP响应,包括一个追踪。对于这个隐蔽的HTTP特性,这里的cookie只包含其追踪的cookie。简单点理解就是如果我们使用了这个方法,就会进行追踪(说白了就是客户端请求成功以后,在响应头里面去存cookie)

loadForRequest方法翻译:将cookie从这个方法加载到一个HTTP请求到指定的url。这个方法从网络上返回的结果可能是一个空集合。简单的实现将返回尚未过期的已接受的cookie去进行匹配。(说白了就是加载url的时候在请求头带上cookie)。

这样,我们通过以上代码就可以完成了Cookie的非持久化。什么,非持久化,这又是神马?

继续给大家科普,在上面说道,Cookie是具有时效性的,所以,Cookie的管理又分为持久化Cookie和非持久化Cookie。非持久化Cookie存储在内存中,也就意味着,其生命周期基本和app保持一致,app关闭后,Cookie丢失。而持久化Cookie则是存储在本地磁盘中,app关闭后不丢失。那么,如果我们要使用Cookie的持久化策略,思想可以参考上面的非持久化策略,只需要将存储方式改一下即可:

A:通过响应拦截器从response取出cookie并保存到本地,通过请求拦截器从本地取出cookie并添加到请求中

B:自定义CookieJar,在saveFromResponse()中保存cookie到本地,在loadForRequest()从本地取出cookie。

那么在这里主要介绍如何通过Okhttp逼格值较高的拦截器去进行持久化cookie操作。

保存cookie拦截器-1

保存cookie拦截器-2

这个SaveCookiesInterceptor拦截器的实现,是首先从response获取set-cookie字段的值,然后通过SharedPreferences保存在本地。

将Cookie添加到请求头

AddCookiesInterceptor请求拦截器,这个拦截的作用就是判断如果该请求存在cookie,则为其添加到Header的Cookie中。

写好这两个拦截器之后,我们只需要将实例对象放进OkhttpClient里面即可快速的完成Cookie持久化操作。(PS:这两个拦截器在同步Cookie的时候也是超级好用)

khttp使用cookie拦截器

拓展:如何通过客户端的cookie与H5上面的cookie进行同步,给大家推荐这一篇文章

客户端与H5同步Cookie

Android-X5WebView封装(Cookie管理、进度监听、适配8.1系统等策略) - 简书


二、Session

Session是对于服务端来说的,客户端是没有Session一说的。Session是服务器在和客户端建立连接时添加客户端连接标志,最终会在服务器软件(Apache、Tomcat、JBoss)转化为一个临时Cookie发送给给客户端,当客户端第一请求时服务器会检查是否携带了这个Session(临时Cookie),如果没有则会添加Session,如果有就拿出这个Session来做相关操作。

在这里引用别人家的一个小故事来加深印象:

在说session是啥之前,我们先来说说为什么会出现session会话,它出现的机理是什么?

我们知道,我们用浏览器打开一个网页,用到的是HTTP协议,了解计算机的应该都知道这个协议,它是无状态的,什么是无状态呢?就是说这一次请求和上一次请求是没有任何关系的,互不认识的,没有关联的。但是这种无状态的的好处是快速。所以就会带来一个问题就是,我希望几个请求的页面要有关联,比如:我在www.a.com/login.php里面登陆了,我在www.a.com/index.php 也希望是登陆状态,但是,这是2个不同的页面,也就是2个不同的HTTP请求,这2个HTTP请求是无状态的,也就是无关联的,所以无法单纯的在index.php中读取到它在login.php中已经登陆了!

那咋搞呢?我不可能这2个页面我都去登陆一遍吧。或者用笨方法这2个页面都去查询数据库,如果有登陆状态,就判断是登陆的了。这种查询数据库的方案虽然可行,但是每次都要去查询数据库不是个事,会造成数据库的压力。 所以正是这种诉求,这个时候,一个新的客户端存储数据方式出现了:cookie。cookie是把少量的信息存储在用户自己的电脑上,它在一个域名下是一个全局的,只要设置它的存储路径在域名www.a.com下 ,那么当用户用浏览器访问时,php就可以从这个域名的任意页面读取cookie中的信息。所以就很好的解决了我在www.a.com/login.php页面登陆了,我也可以在www.a.com/index.php获取到这个登陆信息了。

同时又不用反复去查询数据库。 虽然这种方案很不错,也很快速方便,但是由于cookie 是存在用户端,而且它本身存储的尺寸大小也有限,最关键是用户可以是可见的,并可以随意的修改,很不安全。那如何又要安全,又可以方便的全局读取信息呢?于是,这个时候,一种新的存储会话机制:session 诞生了。

Session 就是在一次会话中解决2次HTTP的请求的关联,让它们产生联系,让2两个页面都能读取到找个这个全局的session信息。session信息存在于服务器端,所以也就很好的解决了安全问题。


三、Token

token是用户身份的验证方式,我们通常叫它:令牌。最简单的token组成:uid(用户唯一的身份标识)、time(当前时间的时间戳)、sign(签名,由token的前几位+盐以哈希算法压缩成一定长的十六进制字符串,可以防止恶意第三方拼接token请求服务器)。还可以把不变的参数也放进token,避免多次查库。

应用场景:

A:当用户首次登录成功(注册也是一种可以适用的场景)之后, 服务器端就会生成一个 token 值,这个值,会在服务器保存token值(保存在数据库中),再将这个token值返回给客户端.

B:客户端拿到 token 值之后,进行本地保存。(SP存储是大家能够比较支持和易于理解操作的存储)

C:当客户端再次发送网络请求(一般不是登录请求)的时候,就会将这个 token 值附带到参数中发送给服务器.

D:服务器接收到客户端的请求之后,会取出token值与保存在本地(数据库)中的token值做对比

对比一:如果两个 token 值相同, 说明用户登录成功过!当前用户处于登录状态!

对比二:如果没有这个 token 值, 则说明没有登录成功.

对比三:如果 token 值不同: 说明原来的登录信息已经失效,让用户重新登录.


Cookie和Session的区别:

1、cookie数据存放在客户的浏览器上,session数据放在服务器上。

2、cookie不是很安全,别人可以分析存放在本地的cookie并进行cookie欺骗,考虑到安全应当使用session。

3、session会在一定时间内保存在服务器上。当访问增多,会比较占用你服务器的性能,考虑到减轻服务器性能方面,应当使用cookie。

4、单个cookie保存的数据不能超过4K,很多浏览器都限制一个站点最多保存20个cookie。

5、所以个人建议:

将登陆信息等重要信息存放为session

其他信息如果需要保留,可以放在cookie中


Token 和 Session 的区别:

session和 token并不矛盾,作为身份认证token安全性比session好,因为每个请求都有签名还能防止监听以及重放攻击,而session就必须靠链路层来保障通讯安全了。如上所说,如果你需要实现有状态的会话,仍然可以增加session来在服务器端保存一些状态。

App通常用restful api跟server打交道。Rest是stateless的,也就是app不需要像browser那样用cookie来保存session,因此用session token来标示自己就够了,session/state由api server的逻辑处理。如果你的后端不是stateless的rest api,那么你可能需要在app里保存session.可以在app里嵌入webkit,用一个隐藏的browser来管理cookie session.

Session是一种HTTP存储机制,目的是为无状态的HTTP提供的持久机制。所谓Session认证只是简单的把User信息存储到Session里,因为SID的不可预测性,暂且认为是安全的。这是一种认证手段。而Token,如果指的是OAuth Token或类似的机制的话,提供的是 认证 和 授权 ,认证是针对用户,授权是针对App。

其目的是让 某App有权利访问 某用户 的信息。这里的Token是唯一的。不可以转移到其它App上,也不可以转到其它 用户 上。转过来说Session。Session只提供一种简单的认证,即有此SID,即认为有此User的全部权利。是需要严格保密的,这个数据应该只保存在站方,不应该共享给其它网站或者第三方App。所以简单来说,如果你的用户数据可能需要和第三方共享,或者允许第三方调用API接口,用Token。如果永远只是自己的网站,自己的App,用什么就无所谓了。

token就是令牌,比如你授权(登录)一个程序时,他就是个依据,判断你是否已经授权该软件;cookie就是写在客户端的一个txt文件,里面包括你登录信息之类的,这样你下次在登录某个网站,就会自动调用cookie自动登录用户名;session和cookie差不多,只是session是写在服务器端的文件,也需要在客户端写入cookie文件,但是文件里是你的浏览器编号.Session的状态是存储在服务器端,客户端只有session id;而Token的状态是存储在客户端。

关于Session、Cookie、Token你知道多少?相关推荐

  1. Session/Cookie/Token还傻傻分不清?

    Cookie.Session.Token 傻傻分不清 Session/Cookie/Token 还傻傻分不清? 相信项目中用JWT Token的应该不在少数,但是发现网上很多文章对 token 的介绍 ...

  2. session,cookie和token,以及负载均衡

    参考 session,cookie,token 负载均衡的session解决办法 转载于:https://www.cnblogs.com/Jamie1032797633/p/11201972.html

  3. 还分不清 Cookie、Session、Token、JWT?

    点击上方蓝色"方志朋",选择"设为星标" 回复"666"获取独家整理的学习资料! 转自:掘金   作者:秋天不落叶 juejin.im/po ...

  4. 设置cookie存活时间_Django之cookie、session、token

    客户端会话技术:cookie 服务端会话技术:session 自定义会话技术:token 一.cookie cookie本身由服务器端生成,通过Response将cookie写到浏览器上,下一次再次访 ...

  5. Spring Session - Cookie VS Session VS Token 以及 Session不一致问题的N种解决方案

    文章目录 Cookie VS Session VS Token History Cookie Session Token Session不一致问题 Session不一致解决方案 nginx sessi ...

  6. Cookie、Session、Token那点事儿

    前言:新公司项目中使用到了Cookie,在各大Android技术讨论群向前辈们取经讨论这cookie.session.token这仨哥们的时候,很多开发者说法不一各抒已见,所以是时候回顾下http基础 ...

  7. postman cookie设置_接口鉴权之cookie,session和token

    什么是接口鉴权? 鉴权就是鉴定权限.在公司开发的一些系统中都会有权限的鉴定.不管是app还是网站的项目,都会有登录模块,而只要有登录模块,他有一些功能,肯定是必须要登录之后才能完成了.比如你在淘宝下单 ...

  8. IM开发基础知识补课(四):正确理解HTTP短连接中的Cookie、Session和Token

    1.前言 众所周之,IM是个典型的快速数据流交换系统,当今主流IM系统(尤其移动端IM)的数据流交换方式都是Http短连接+TCP或UDP长连接来实现.Http短连接主要用于从服务器读取各种持久化信息 ...

  9. 【学习笔记】cookie、session、token和分布式session

    文章目录 cookie和Session session和token cookie和token总结 分布式Session cookie和Session 为什么要有session的出现? 答:是由于网络中 ...

  10. chrome session丢失_一文带你彻底读懂Cookie、Session、Token到底是什么

    在了解这三个概念之前我们先要了解HTTP是无状态的Web服务器,什么是无状态呢?就像上面夏洛特烦恼中经典的一幕对话一样,一次对话完成后下一次对话完全不知道上一次对话发生了什么.如果在Web服务器中只是 ...

最新文章

  1. Linux期末复习编程题
  2. AGS Server 10.1 切图工具
  3. 1-4 数组元素的区间删除 (20 分)
  4. 【LeetCode笔记】剑指 Offer 31. 栈的压入、弹出序列 (Java、栈)
  5. 小米组织架构再调整:手机部成立参谋部 朱磊出任参谋长
  6. 罗永浩的公司被收购,还清债务指日可待
  7. 质量和品质的区别_质量体系认证,与产品质量认证的区别 !
  8. JavaScript:继承详解
  9. ConceptDraw Office Pro v8.0.2 Keygen
  10. Unity3D游戏资源的提取
  11. winrar打包bat成exe并自动运行
  12. 教育教学教师竞聘说课PPT模板
  13. 关于单链表中temp.next、head.next的理解
  14. MinIO异常the region is wrong; expecting ‘us-east-1‘
  15. linux 系统重启过程,linux 系统启动流程
  16. oracle修改分区表的默认空间,Oracle数据库学习_Oracle分区表的分区占用空间为什么是8M?如何修改分区的初始空间?...
  17. layui模块显示收缩_修改layui的后台模板的左侧导航栏可以伸缩的方法
  18. 几款实用的内网穿透工具,推荐
  19. 无心剑英译吴飞《经纬之歌》(泸州职业技术学院形象宣传歌曲)
  20. Python办公自动化学习笔记--Word操作

热门文章

  1. windows环境安装elasticsearch
  2. 携程基于云的软呼叫中心及客服平台架构实践\n
  3. css 固定宽度,自动换行
  4. 采用C#泛型实现数据库之间的切换
  5. utf-8和gbk的区别
  6. 应用程序框架实战四:你需要应用程序框架吗
  7. usermod 添加用户多个附属组
  8. QuickServer开发指南(1)- 介绍
  9. BZOJ4072[Wf2014] baggage
  10. git学习笔记-(11-git存储)