打造千万级流量秒杀第十课 Web 安全:如何解决重放攻击和 XSS 注入?

144 篇文章 29 订阅
102 篇文章 10 订阅

上一讲,我给你介绍了 KV 存储。虽然用了 KV 存储后,服务整体性能和可用性都得到了提升,但是如果有人恶意捣乱,效果也会大打折扣。举个例子,如果秒杀系统有安全漏洞,导致有1/3 的是利用漏洞发起的恶意请求,那这部分就会带来存储开销,白白浪费了 1/3 的存储资源。

从系统角度来看,这可能是小事,仅仅降低了一些可用性,但它给公司造成的经济损失却很大。比如,有人可能会利用漏洞快速重复提交订单,导致用户在活动中享受多笔订单优惠。更严重的是,假如黑客利用漏洞执行一些恶意操作,如获取或者篡改系统数据或者权限,这可能导致用户数据泄漏,进而被告上法庭。

现在你意识到 Web 安全的重要性了吧。那我们该如何防范 Web 安全问题呢?这就是本讲我要给你重点介绍的内容了。希望学完后,你能轻松应对一些常见的 Web 安全问题。

Web 安全风险有哪些?

作为软件工程师,我们通常需要注意哪些 Web 安全风险呢?我的建议是,可以参考 OWASP Top 10 。

什么是 OWASP 呢?OWASP 是 Open Web Application Security Project 的缩写,它是一个组织,中文名称叫“开放式Web应用程序安全项目”。OWASP 每年都会发布排名前十的 Web 安全风险,也就是前面提到的 OWASP Top 10 。比如 2020 年 OWASP Top 10 如下:

  1. 注入

  2. 失效身份验证和会话管理

  3. 敏感信息泄露

  4. XML 外部实体注入攻击(XXE)

  5. 存取控制中断

  6. 安全性错误配置

  7. 跨站脚本攻击(XSS)

  8. 不安全的反序列化

  9. 使用具有已知漏洞的组件

  10. 日志记录和监控不足

Lark20201211-210552.png
这 10 种风险在这里我就不一一介绍了,重点为你介绍下 Top 1 “注入”,因为它的风险最高。为什么这么说呢?

“注入”允许攻击者上传一段可解释执行的代码片段,而该代码片段可能帮助攻击者获取系统管理权限或者隐私信息。比如,黑客可能通过“SQL 注入”获取数据库表中所有的用户名和密码,或者通过“shell 脚本注入”等方式获取系统管理权限,进而危害整个系统的安全。

实际上,Top 4 XXE 和 Top 7 XSS 也是利用了“注入”来实现的。XXE 主要是将恶意代码注入 XML 文件中,利用服务器解析 XML 文件的漏洞来获取服务器上的额外数据。而 XSS 主要是利用浏览器渲染前端页面的漏洞,将恶意代码注入页面的数据中,窃取用户信息或执行恶意操作。

“注入”的攻击对象主要是两类:

  • 针对系统的注入,主要用于在系统中执行恶意代码,如利用“shell脚本注入”上传获取系统权限的脚本;

  • 针对用户的注入,主要用于获取用户身份信息并执行损害用户利益的操作,如利用 XSS 获取用户登录信息并发起转账请求。

除了以上因系统自身缺陷导致的风险外,攻击者还有一些利用网络缺陷发起的攻击手段,比如:中间人攻击、重放攻击、DDoS 攻击。

中间人攻击, 简单来说就是攻击者通过技术手段,侵入发送方和接收方之间的计算机(如网络代理服务),拦截网络请求窃取并篡改数据。我们通常可以利用加密等方式有效防止中间人攻击,如使用 HTTPS 代替 HTTP。

什么是重放攻击呢?所谓重放攻击,就是把以前发过的数据原封不动地重新发送给接收方。这个发过的数据,可能是攻击者窃听到的别人的数据,也有可能是攻击者曾经自己发过的数据。

重放攻击通常用来恶意消耗 Web 系统有限的资源,比如某电商平台的竞争对手或者恶意用户可能利用重放攻击来恶意占用爆款商品的库存,或者在秒杀活动的时候快速刷走活动商品。我们熟悉的“黄牛”,就是利用“秒杀器”之类的工具,快速提交重复的请求来刷走秒杀商品。

DDoS 攻击又是什么呢?DDoS的全称是 Distributed Denial of Service,即“分布式拒绝服务”,它的前身是 DoS (Denial of Service,拒绝服务)。DDoS 攻击通常是利用大量计算机同时向服务器发送大量垃圾数据,让服务器因为资源限制而无法处理正常的用户请求。

你发现没有,重放攻击和 DDoS 攻击有个相同点:都是利用大量请求快速占用系统资源。有时候,当重放攻击的请求量达到一定量级(如单节点达到 1000 次),就发生质的转变,可视为 DDoS 攻击。目前各大云产商基本都有预防 DDoS 攻击的能力。

对于秒杀系统来说,由于涉及钱和货,系统资源和用户信息都很重要,而重放攻击和 XSS 会危害到这两方面的安全。所以,接下来我将详细为你介绍下如何预防这两方面的安全风险 。

如何预防重放攻击?

前面我们了解到,重放攻击主要是将发送过的数据重新发送给接收方。试想下,如果我们能将这些关键的数据打上唯一标识,并在接收端记录下是否已经接收过,是不是就能预防重放攻击了呢?没错,就是这个思路!那具体是怎么做呢?

通常有三种方法预防范重放攻击:加随机数、加时间戳、加序列号。

加随机数,我们可以让后端生成一个随机数给前端,并将该随机数记录为未使用,同时设置有效期。在后续前后端交互中,后端会接收前端请求,并校验是否有该随机数,是否未使用,是否未过期。如果请求中没有该参数,或者该随机数已使用或者已过期,则拒绝请求。

这个方法的优点是不容易伪造,但它需要额外保存使用过的随机数,若记录的时间段较长,则保存和查询的开销较大。

加时间戳, 我们可以在前端生成一个时间戳,然后把它作为参数发给后端,后端校验该时间戳与当前时间是否相差在一个允许的范围内(比如 10 秒),如果超过了,则拒绝请求。

该方法优点是不用像加随机数那样额外保存其他信息,但前端和后端认证双方需要准确的时间同步,同步越好,受攻击的可能性就越小。所以,当系统变得庞大时,跨越的区域较广,要做到精确的时间同步就变得不容易了。

加序列号, 每次请求或返回的时候,我们都可以在上一次请求或返回的序号上加 1 ,并将当前序号记录下来。如果收到不连续的序号,则认为是非法数据。

该方法优点是不需要时间同步,保存的信息量比随机数方式小。缺点是一旦攻击者对报文解密成功,就可以获得流水号,从而每次将流水号递增欺骗认证端。

以上三种方法各有优缺点,那么秒杀系统该使用哪种方法呢?

我们都知道,一个正常用户在发起抢购商品的请求前,需要先进入秒杀活动页或者商品详情页,而这两个页面都会请求后端接口,以获取活动信息和商品信息。基于此,我们就可以利用这两个页面来做文章。

具体来说,就是在这两个页面调用后端接口的时候,由后端给前端下发一个短时间内可以作为唯一标识的东西,比如用随机数和时间戳拼接得到的数字。同时,后端将这个唯一标识记录下来,有效期设置为活动结束时间。

当用户在前端发出请求抢购商品的时候,后端从抢购接口处接收到请求,此时它先判断是否有该唯一标识,如果没有该标识或者该标识已经被用过,则拒绝请求。

由于唯一标识的生成算法是由后端控制,攻击者无法伪造,只能通过接口获取。所以,当攻击者通过接口获取唯一标识的时候,我们可以对攻击者进行常规限流,如限制每个 IP 每秒请求数。

需要注意的是,秒杀系统最好开启代理层的粘性会话(Sticky Session)功能,以便将同一个用户的请求转发到同一个服务节点。这样就可以利用服务节点的本地内存缓存,来快速校验唯一标识,以及针对 IP 限流。

以上就是防重放攻击的方法,你学会了吗?

如何防 XSS ?

前面提到了“注入”的风险,比如在提交表单的时候,攻击者可能在表单某个字段里填上一段可被系统执行的脚本代码。如果系统没有安全校验并执行了该代码的话,可能就会遭到攻击者入侵,导致用户数据泄漏。

举个例子,某系统查询账号信息的 SQL 可能是这样拼接而成的:

"SELECT * FROM accounts WHERE custID='" + ID + "'"

如果攻击者将参数 ID 填写为:

or '1'='1'

这将会导致所有账号信息被泄漏。

XSS 产生的本质原因和这个类似,也是通过前端传入非法脚本代码到后端。只不过与 SQL 注入不同的是,XSS 是在前端获取用户信息并发起非法请求,而 SQL 注入是在后端获取用户信息。

我们要怎么防范 XSS 风险呢?

首先,我们要对前端输入的数据进行校验,过滤掉非法关键字。比如,我们可以让前端对商品图片 URL 输入框的数据进行校验,过滤掉诸如“javascript:”这样的前端关键字。

其次,后端对前端输入的数据进行转码后,再存入数据库,如进行 URLEncode 和 Escape 。在拼接 SQL 语句的时候,不要用简单的字符串拼接,而是利用占位符和参数通过 SQL 语句生成函数的来生成,如下所示:

sql := mysql.Raw("SELECT * FROM accounts WHERE custID='?'", ID)

这样可以利用 SQL 语句生成函数来校验参数合法性。
最后,前端在页面渲染的时候,也需要注意对一些关键字段进行字符转义,比如对字符串中的单引号(')、双引号(")、尖括号(<>)进行转义,就能防止前端利用这些数据渲染页面的时候执行攻击者注入的 javascript 代码。

以上便是防范 XSS 的方法。你学会了吗?

小结

这一讲我给你介绍了一些常见的 Web 安全风险,以及常用的防范手段。相信现在你对 Web 安全已经有了初步的认识。那么,你是否能将他们应用到自己的工作当中呢?

思考题:如果无法通过秒杀活动页下发唯一标识,我们该采用什么方法防重放攻击呢?

你可以把答案写在留言区。期待你的回答哦!

这一讲就介绍到这里了,下一讲我将为你介绍如何通过系统参数,按业务场景优化网络性能。

2.png


精选评论

**振:

同一用户或同一IP的访问频次?

    讲师回复:

    针对用户和 IP 的是限流。防重放是针对单个请求的,目的是防止相同数据重复提交。举个例子:UI 上不小心点了两次提交按钮,可能就触发了两次相同参数的下单请求,但系统应该只执行一次。

**3655:

重放攻击那里说再加个接口搞唯一标识 再对这个接口搞个限流

    讲师回复:

    这个接口是用于下发唯一标识,后续下单请求带上该唯一标识,下单请求完了后该唯一标识失效。

**个咪的汪:

可以用request的header内的数据来限制客户端不能重复提交吗?或者ip

    讲师回复:

    即使用 header 或者 ip,也需要确保请求是唯一的。

**用户0528:

还有更多的方法么,这些好像很常见,有没有大厂独有的利器

    讲师回复:

    Web 安全的防范依赖 Web 技术,而 Web 技术本身比较成熟,所以方法比较通用。一些简单的 Web 安全防范,可以借助云厂商提供的 WAF 来做,但跟具体业务相关的就需要业务服务自己处理了。不同公司,可能区别也就是在于一些关键字段名称不一样,校验的逻辑不一样。用的技术可能也有差异,比如用的前端、后端框架不一样,遇到的问题也会有差异。

  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 2
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

办公模板库 素材蛙

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值