Loading

Restful 接口测试基础

做接口测试时,经常会接触到 get、post,token、cookie、session,关于他们的区别,这里详细记录一下。

Get 与 Post 的区别

通过 curl 发送两个请求,保存信息到文件内,进行比较。

$ curl -s "http://httpbin.org/status/200" -v &>/tmp/get
$ curl -s "http://httpbin.org/status/200" -d "a=1" -v &>/tmp/post

diff check

  • http 的 method 字段不同
  • 数据传输方式不同
    • get:以 ?分割 URL 和传输数据,参数之间以 & 相连
      • 英文 + 数字 会原样发送
      • 空格会转换为 +
      • 中文或者其他字符,会转为 base64
    • post:数据存放在 body 内进行传输,可以支持 form、json、xml、binary 等各种数据格式
  • post 请求的响应头带有 Content-LengthContent-Type
    • Content-Length 代表 body 的长度,这个长度必须精准
    • Content-Type 代表响应的数据格式
  • 行业通用的规范
    • 无状态变化的建议使用 get 请求
    • 数据的写入与状态的修改建议使用 post 请求

cookie 是一个非常具体的东西,指的就是浏览器里面能永久存储的一种数据,仅仅是浏览器实现的一种数据存储功能。

cookie 由服务器生成,发送给浏览器,浏览器把 cookie 以 kv 形式保存到文本文件内,下次请求同一网站时会把该 cookie 发送给服务器。由于 cookie 是存在客户端上的,所以浏览器加入了一些限制确保 cookie 不会被恶意使用,同时不会占据太多磁盘空间,所以每个域的 cookie 数量是有限的,且每个域的 cookie 只作用于自己的网站。

Session

session 从字面上讲,就是会话。这个就类似于你和一个人交谈,你怎么知道当前和你交谈的是张三而不是李四呢?对方肯定有某种特征(长相等)表明他就是张三。

session 也是类似的道理,服务器要知道当前发请求给自己的是谁。为了做这种区分,服务器就要给每个客户端分配不同的“身份标识”,然后客户端每次向服务器发请求的时候,都带上这个“身份标识”,服务器就知道这个请求来自于谁了。至于客户端怎么保存这个“身份标识”,可以有很多种方式,对于浏览器客户端,大家都默认采用 cookie 的方式。

服务器使用 session 把用户的信息临时保存在了服务器上,用户离开网站后 session 会被销毁。这种用户信息存储方式相对 cookie 来说更安全,可是 session 有一个缺陷:如果web服务器做了负载均衡,那么下一个操作请求到了另一台服务器的时候 session 会丢失。

Token

Token 是服务端生成的一串字符串,以作客户端进行请求的一个令牌,当第一次登录后,服务器生成一个 Token 返回给客户端,以后客户端只需带上这个 Token 前来请求数据即可,无需再次带上用户名和密码。

最简单的 token 组成:

  • uid(用户唯一的身份标识)
  • time(当前时间的时间戳)
  • sign(签名,由token的前几位+盐以哈希算法压缩成一定长的十六进制字符串,可以防止恶意第三方拼接 token 请求服务器)

使用 Token 的目的是为了减轻服务器的压力,减少频繁的查询数据库,使服务器更加健壮。

传统身份验证

HTTP 是一种没有状态的协议,也就是它并不知道是谁访问应用。客户端通过用户名和密码进行身份验证后,再次发送请求,还得验证一下。

解决办法:用户身份验证通过后,在服务端会生成一条记录用来保存用户数据,然后把这条记录的 ID 号发送给客户端,客户端将收到的 ID 号存储在 Cookie 里。客户端再次发送请求的时候,带着 Cookie 信息,服务端收到请求后会验证 Cookie 信息是否已经存在,如果存在,说明用户已经通过了身份验证,就把用户请求的数据返回给客户端。

这就是 Session 的工作流程,服务端保存登录用户的信息,并返回 sessionId,sessionId 可以放在请求的 cookie 或 query 中标记。Session 并不是永久性存储,服务端会定期清理过期的 Session 。

基于 Token 的身份验证

使用基于 Token 的身份验证方法,在服务端不需要存储用户的登录记录。大概的流程是这样的:

  • 客户端使用用户名跟密码请求登录
  • 服务端收到请求,去验证用户名与密码
  • 验证成功后,服务端会签发一个 Token,发送给客户端,Token 可以设置有效期
  • 客户端收到 Token 以后存储起来,比如放在 Cookie 里或者 Local Storage 里
  • 客户端每次向服务端发起请求都需要带着 Token
  • 服务端收到请求,验证 Token 的真实性和有效期
    • 成功,向客户端返回数据
    • 失败,返回错误信息,重新登录

Token 是个凭据,丢失后可以重新认证。当然也会存在泄漏问题,比如别人拿到你的手机,获取到 Token,在过期之前就都可以以你的身份在别的地方登录。

解决这个问题办法:将请求URL、时间戳、Token 三者进行合并加盐签名,服务端校验有效性。

  1. cookie 数据存放在客户端上,session 数据放在服务器上。

  2. cookie 不安全,别人可以分析存放在本地的 cookie 进行复用,考虑到安全应当使用session。

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

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

  5. 一般将登录等重要信息存放为 SESSION,其他信息如果需要保留,可以放在 COOKIE 中。

session 与 token 的区别

  1. session 和 token 并不矛盾,作为身份认证 token 安全性比 session 好,因为每个请求都有签名还能防止监听以及重放攻击。

  2. Session 是一种 HTTP 存储机制,目的是为无状态的 HTTP 提供的持久机制。所谓 Session 认证只是简单的把用户信息存储到 Session 里,因为 SID 的不可预测性,暂且认为是安全的,这是一种认证手段。 而 Token,如果指的是 OAuth Token 或类似的机制的话,提供的是认证授权,认证是针对用户,授权是针对应用。其目的是让应用有权利访问用户的信息。这里的 Token 是唯一的。不可以转移到其它 App 上,也不可以转到其它 用户 上。

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

打破误解

“只要关闭浏览器 ,session 就消失了?”

不对。对session来说,除非程序通知服务器删除一个 session,否则服务器会一直保留,程序一般都是在用户做 log off 的时候发个指令去删除 session。

然而浏览器从来不会主动在关闭之前通知服务器它将要关闭,因此服务器根本不会有机会知道浏览器已经关闭。

之所以会有这种错觉,是大部分 session 机制都使用会话 cookie 来保存 session id,而关闭浏览器后这个 session id 就消失了,再次连接服务器时也就无法找到原来的 session。如果服务器设置的 cookie 被保存在硬盘上,或者使用某种手段改写浏览器发出的 HTTP 请求头,把原来的 session id 发送给服务器,则再次打开浏览器仍然能够打开原来的 session.

恰恰是由于关闭浏览器不会导致 session 被删除,迫使服务器为 session 设置了一个失效时间,当距离客户端上一次使用 session 的时间超过这个失效时间时,服务器就可以以为客户端已经停止了活动,才会把session 删除以节省存储空间。

来源

posted @ 2023-03-08 14:24  ABEELAN  阅读(90)  评论(0编辑  收藏  举报