一、XSS 攻击
1、原理
XSS(Cross Site Scripting):跨域脚本攻击。 是 web 攻击最常见的手段之一,它通过对网页注入恶意可执行代码且成功被浏览器执行,从而达到攻击的目的。(比如在url、评论框中输入js、hmtl 代码块等)。
2、分类
- 反射型(非持久型):攻击者通过构造一个带有恶意代码的
url链接诱导用户点击,只有当用户访问这个url才会执行; - 存储型(持久):攻击者将带有恶意代码的内容发送给服务器(如:评论框),服务器直接将内容存储到数据库中,其他用户请求访问该内容时,就会执行代码;
DOM型:主要与前端js有关,通过脚本恶意修改DOM结构。
3、防范措施
(1)对字符串进行编码, 对 url 的查询参数进行转义(反射型);
(2)对数据进行 转义/过滤 : (适用于所有类型)
- 前端数据传递给服务器之前,先转义/过滤(防范不了抓包修改数据的情况),
- 服务器接收到数据,在存储到数据库之前,进行转义/过滤,
- 前端接收到服务器传递过来的数据,在展示到页面前,先进行转义/过滤;
下面是一个简易版对用户的输入进行过滤的方法:
function escapeHTML(str) {
str.replace(/[<>& "]/g, function(match) {
switch (match) {
case '<':
return '<';
case '>':
return '>';
case '&':
return '&';
case ' ':
return ' ';
case '"':
return '"';
}
});
}
(3)对用户的输入使用 innerText 或者 textContent 进行设置,而不是使用 innerHTML 或者 outerHTML 进行设置(DOM型);
(4)CSP (Content-Security-Policy) 安全内容策略:建立白名单,告诉浏览器哪些外部资源可以加载和执行;
(5)关键请求使用验证码,比如转账请求,避免恶意脚本发送这些关键请求;
(6)服务器端设置 cookie 为 httpOnly 让前端无法通过 js 获取到用户的 cookie。
二、 CSRF 攻击
1、原理
SRF(Cross-site request forgery):跨站请求伪造。
条件:
- 登录受信任网站
A,并在本地生成Cookie。(如果用户没有登录网站A,那么网站B会诱导你登录网站A)。 - 在不登出
A的情况下,访问危险网站B(其实是利用了网站A的漏洞)。
2、CSRF的特点
- 攻击一般发起在第三方网站,而不是被攻击的网站。被攻击的网站无法防止攻击发生。
- 攻击利用受害者在被攻击网站的登录凭证,冒充受害者提交操作;而不是直接窃取数据。
- 整个过程攻击者并不能获取到受害者的登录凭证,仅仅是“冒用”。
- 跨站请求可以用各种方式:图片
URL、超链接、CORS、Form提交等等。部分请求方式可以直接嵌入在第三方论坛、文章中,难以进行追踪。
CSRF通常是跨域的,因为外域通常更容易被攻击者掌控。但是如果本域下有容易被利用的功能,比如可以发图和链接的论坛和评论区,攻击可以直接在本域下进行,而且这种攻击更加危险。
3、防范措施
(1)token:token 验证的 CSRF 防御机制是公认最合适的方案。但若网站同时存在 XSS 漏洞的时候,这个方法也是空谈;
(2)验证码:强制用户必须与应用进行交互,才能完成最终请求。此种方式能很好的遏制 CSRF,但是用户体验比较差;
(3)Referer check:请求来源限制,此种方法成本最低,但是并不能保证 100% 有效,因为服务器并不是什么时候都能取到 Referer,而且低版本的浏览器存在伪造 Referer 的风险。
三、XSS 与 CSRF 区别
(1)CSRF:需要用户先登录网站 A,获取 cookie。XSS:不需要登录;
(2)通常来说 CSRF 是由 XSS 实现的,CSRF 时常也被称为 XSRF(CSRF 实现的方式还可以是直接通过命令行发起请求等);
(3)本质上讲,XSS 是代码注入问题,CSRF 是 HTTP 问题。 XSS 是内容没有过滤导致浏览器将攻击者的输入当代码执行。CSRF 则是因为浏览器在发送 HTTP 请求时候自动带上 cookie,而一般网站的 session 都存在 cookie 里面(Token验证可以避免)。