我知道现在的避免 crsf 做法,也看过 django 的中间件的实现.
但是,恶意网站所能做的事情很少啊,比如他是不能任意添加 HEAD 的,这是 cors 的限制,简单请求你只能自定义那几个方法,复杂请求更安全了,恶意网站都发不了请求. (这句话对吗?)
所以我们可以直接在后端验证一下有没有自定的 header, 对应的值对不对,注意这个是静态的 header,整个网站都一样的.
但是没人这么做过,应该是不对,所以请问各位那里错了?
我找到老外的讨论了,stackexchange质量更高一点, sof的相同问题 同 v2, 答题质量就很差.可能大部分人都先入为主了.
我的观点是正确的.不用 token 是可以的,不过不是最佳实践而已,有很多理由来反对我.比如回复里有人提到的 Flash 问题.双重保险嘛.
而且还真有人是真么干的,我没点进去 This is how Jersey 1.9's CsrfProtectionFilter works and it is described in this blog post: http://blog.alutam.com/2011/09/14/jersey-and-cross-site-request-forgery-csrf/.
资源: http://security.stackexchange.com/questions/22903/why-refresh-csrf-token-per-form-request
1
airyland Oct 28, 2016
后端直接发啊,哪有 cors 限制。。
|
2
murmur Oct 28, 2016
最简单对付 crsf 不就一个 token 的事么 有那么复杂么 何况防重复提交的表单不考虑 crsf 也都加了 token 吧
|
3
jugelizi Oct 28, 2016
cors 是浏览器的功能
谁知道万一浏览器厂商出个 bug 可以绕过呢 还是 flash 可没限制自定义 header |
4
mdzz Oct 28, 2016
用户输入是不可信的。—— 佚名(到底谁说的
|
10
petelin OP @jugelizi 这个解释比较合理...那要这么说的话,我们把 token 放在 cookie 里也不保险,万一浏览器有问题,恶意网站能拿到 cookie 里的值然后放在 post 中呢 /
|
11
shiji Oct 28, 2016
难道不是 CSRF 么?楼主把二楼都给带顺拐了。
|
13
glasslion Oct 28, 2016
crsf 主要防的的劫持 form 提交(xss), 而 表单提交是 无法设置 http header 的。
cors 和 csrf 有毛线关系 |
14
GG668v26Fd55CP5W Oct 28, 2016 via iPhone
csrf 处理 ajax 请求一般就是在 head 附一个特殊字段
|
15
mdzz Oct 28, 2016 CRSF 全称 Cross Site Request Forgery ,跨站请求伪造。用我话说恶意网站 B 站在用户不知情的情况下操作了 A 站的用户资源状态。 —— 沃·兹基硕德
(该去看眼科了 |
16
GG668v26Fd55CP5W Oct 28, 2016 via iPhone
@falcon05 但 header 的这个字段是动态的,或者说有过期时间
|
17
gamexg Oct 28, 2016 @glasslion +1
需要考虑哪个方案简单,哪个方案兼容性高。 在表单加一个隐藏字段轻松解决,为什么要自己构建 post 请求并添加 header ? 而且 header 兼容性并不好: https://developer.mozilla.org/zh-CN/docs/Web/API/XMLHttpRequest/setRequestHeader |
19
petelin OP @gamexg 有道理,直接添加静态变化字段是很好的解决方案.
但是如果我提供的全是 api 呢,django 给出的方案是 cookie+post+token, 而我觉得直接在 ajax 提交的时候设置特殊 *静态 * HEAD, 服务器校验就好,即解决了问题,又不复杂. |
20
Mutoo Oct 28, 2016
“恶意网站 B ” 这个定义就很宽泛的,可以是一个你常去的公共论坛,你根本不会注意,然后某个帖子别人插入了一个 img (大部分论坛都允许的)。但是这个 img 的 url 是目标网站 A 的一个 GET 请求地址。一般人访问这个帖子什么也不会发生,但是如果是目标网站的管理员,并且是登陆状态。那么这个 GET 请求就可能触发相应的功能,达成 CRSF 。这个过程黑客只需要构造一个有效的 GET 请求,其它都不需要做,甚至不需要弄到 cookie 。
防 CRSF 的过程就是让黑客无法构造有效的 GET 请求,例子让 get 请求带上 token ,该 token 由服务端生成,并设置有效期。 |
22
gamexg Oct 28, 2016
|
23
GG668v26Fd55CP5W Oct 28, 2016 via iPhone
@Mutoo 如果按规范的话, GET 请求不会改变服务器状态,所以 csrf 并不需要对 get 请求处理。但是很多网站并没有按套路出牌……
|
24
GG668v26Fd55CP5W Oct 28, 2016 via iPhone
@petelin 习惯吧,因为觉得 token 跟 cookie 有关系,而 cookie 是有过期时间的,所以习惯性地也把 header 的 token 搞一个过期时间,我记得 CI 框架就是有这个配置,其实我觉得静态 header 的 token 也未尝不可
|
25
Mutoo Oct 28, 2016
@falcon05 确实,把 token 放在 X-CSRF-TOKEN 里更合理些。
静态的 header 并不安全。如果黑客对恶意网站有完整的控制权,可以直接伪造完整的 request 。一样可以 CSRF |
26
billlee Oct 28, 2016 自定义 header 肯定能防 csrf, 但是,但那毕竟要用 ajax 才能实现,如果不用 javascript, 就只能用 csrf token 了。
|
29
oott123 Oct 28, 2016
🌚仅对 10 楼:如果恶意网站能拿到你的 cookie ,那它也用不着去 csrf 你了。
|
30
cmxz Oct 28, 2016 via Android 楼主的想法确实没错。
另外 CORS 在发添加自定义 header 的请求前会发送预检请求( options ),如果服务端不对预检请求做正确响应,那么 CORS 的自定义 header 是无法发出的。 flash 的跨域,如果我没有记错的话, 1.域名下的 crossdomain.xml 中别随便授权域 2.本域和 crossdomain.xml 中授权的域下别随便放网上找到 swf 文件 3.本域和 crossdomain.xml 中授权的域下别随便允许上传文件(非 swf 的也不能允许,如果因业务必须允许,那需要做一些其他的操作,就不详述了) 做好以上 3 点,应该就 ok 了 ps :从回帖看 v2 上好多人都没完全理解 csrf |
32
msg7086 Oct 29, 2016
没记错的话 CSRF 是早于 CORS 出现的。
|