在大前端时代的安全文章中, Web 前端和 Native 如何从数据安全层面制定客户端的反爬虫策略本文将从 开始API 在数据接口层面谈技术方案,实现数据安全。
一、 API 接口要求安全问题
API 界面存在许多常见的安全问题,如下
因此,对上述问题也有一些解决方案:
关于 HTTPS 双向认证和 证书Web 端反爬虫技术方案在大前端时代的安全性一文中有具体说明。接下来,本文的主角是防重放
二、 要求参数防篡改
前一篇文章也讲过,HTTPS 仍然可以抓包的,造成安全问题。抓包工具下的数据还是裸奔的,可以查看Charles如何从入门到精通文中获得 HTTPS 数据。
假如通过网络层高手截获 HTTPS 证书认证后的数据需要签署请求参数。步骤如下:
- 客户端使用约定的密钥加密请求参数并获得签名 signature。并将签名添加到请求参数中,发送到服务端
- 服务端接收客户端请求,使用约定的密钥对请求参数(不包括 signature)再签名,得到值 autograph
- 对比 服务器signature 和 autograph,相等认为是合法请求,否则认为参数被篡改,判定为非法请求
因为中间人不知道签名密钥,即使拦截请求并修改参数,也无法获得正确的签名 signature,服务器将此类结构的请求判定为非法请求。
三、防重放策略
在工程师文化中,要做一件事,首先要定义它。我们可以知道该做什么,该怎么做。
理论上,一个 API 接口请求已收到,服务将进行验证。然而,当一个法律请求被中间人拦截时,中间人会完好无损地重复一次或多次发送请求。这种重复使用法律请求进行的攻击被重放。
重放会造成服务器问题,需要防止重放。本质上就是如何区分正常合法的请求。
3.1 基于 timestamp 的方案
理论上,客户端发起请求,在服务端接收请求的时间不超过60秒。利用这一特点,客户端每次都会添加 timestamp1,客户端将 timestamp1 与其他请求参数签名signature,之后发送请求到服务器。
- 服务器当前时间戳 timestamp2,timestap2 - timestamp1 > 60s,则认为非法
- 服务端接收客户端请求,使用约定的密钥对请求参数(不包括 signature、timestamp1)进行再次签名,得到值 autograph。比对 signature 和 autograph,如果不相等,则视为非法请求
如果中间人拦截请求,修改 timestamp 或任何其他参数,但不知道密钥,因此服务器仍被判定为非法请求。
一般来说,中间人在抓取包、篡改参数和发起请求的过程中超过60秒,因此服务器仍将被判定为非法请求。
基于 timestamp 的设计缺陷也很明显。由于各种原因,请求将在60秒内钻出规则漏洞,服务器将被判定为合法请求。
3.2 基于 nonce 的方案
由于时间戳会有漏洞,新方案是基于随机字符串 nonce。也就是说,每个请求都添加一个随机字符串,然后用密钥加密其他参数以获得签名 signature。服务端收到请求后
- 先判断 nonce 参数是否存在于某个集合中,如果存在,则视为非法请求;如果没有, nonce 添加到当前的集合中
- 服务端将客户端请求参数(除 nonce) 用密钥加密autograph,将 signature 和 autograph 比较不相等,认为是非法请求
然而,该方案也有缺点,因为当前的请求需要与集合搜索匹配,因此集合不能太大,否则匹配算法特别耗时,界面性能降低。因此,必须定期删除部分 nonce 值。但在这种情况下,被删除的 nonce 被用作重放攻击,服务器被判定为合法请求。
假设服务器只保存在24小时内要求的 nonce,存储仍然是一笔不小的开支。
3.3 基于 timestamp nonce 的方案
根据 timestamp 和 nonce 各自的特点:timestamp 60秒内无法解决重放请求;nonce 存储和搜索消耗很大。因此,结合两者的特点, 「timestamp nonce 防重放方案」。
- 利用 timestamp 解决60秒以上被认为是非法请求的问题
- 利用 nonce 解决 timestamp 60秒内漏网的鱼
步骤:
不得直接操作文件或数据库,否则服务端 IO 太多,导致性能瓶颈。可以是 mmap 或者其他内存到文件的读写机制。根据场景可以选择乐观锁、悲观锁。
其中一个 timestamp对于 的问题,服务器将要求 的参数timestamp 判断差异的致命缺点之一是服务器和客户端之间的时间差。当然,您也可以通过验证时间戳来解决这个问题。请继续查看以下部分。
四、 计算机网络时间同步技术原理
在许多场景中,客户端和服务端的时间同步非常重要,例如,这些场景经常发生。
- 商品秒杀系统。用户打开页面,浏览各类商品。商品列表界面右侧和详细信息页面具有倒计时秒杀功能。用户在详细信息页面购买、下单和结算。发现弹出提示“商品库存不足,请购买其他类似品牌的商品”
- 一个答题系统,题目是公司的核心竞争力。有心的程序员为界面设计了「防重放」功能。但是前端小哥不给力,接口带过去 timestamp 与服务器不在同一时区,差几秒钟。别有用心的竞争产品公司的爬虫工程师发现了这个漏洞,并爬行了主题数据。
因此,这种现象在计算机领域非常普遍,有解决方案。
如果精度要求不高:请求服务器上的时间 ServerTime,然后同时记录当前时间 LocalTime1;当需要获得当前时间时,使用最新当前时间 (LocalTime2 - LocalTime1 ServerTime)
拿 iOS 端举例:
- App 启动后通过接口获取服务器时间 ServerTime,保存本地。同时记录当前时间 LocalTime1
- 当需要使用服务器时间时,首先获得当前时间 LocalTime2 - LocalTime1 ServerTime
- 如果服务器时间接口失败,则从缓存中获得以前的同步结果(初始时间为 App 包装阶段内置)
- 使用 NSSystemClockDidChangeNotification 监测系统时间发生改变,若变化则重新获取接口,进行时同步
如果需要更高的精度,如 100纳秒,则需要使用 NTP(Network Time Protocol)网络时间协议,PTP (Precision Time Protocol)协议的准确时间同步。
原文链接:https://segmentfault.com/a/1190000021922705