php HTTP_ORIGIN 的安全性如何?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/4566378/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
How secure is HTTP_ORIGIN?
提问by murvinlai
I want to find out whether an incoming HTTP_REQUEST call from a third party website is coming from the list of domains that I defined.
我想查明来自第三方网站的传入 HTTP_REQUEST 调用是否来自我定义的域列表。
I know that HTTP_REFERER can be used to find out where the third party domain is, but it is not secure enough. People can spoof it or use Telnet to fake it.
我知道可以使用 HTTP_REFERER 来查找第三方域的位置,但它不够安全。人们可以欺骗它或使用 Telnet 来伪造它。
So, how about HTTP_ORIGIN? Is it sent from all browsers? Is it secure?
那么,HTTP_ORIGIN 怎么样?它是从所有浏览器发送的吗?它安全吗?
Also, can people fake the REMOTE_ADDR in a HTTP_REQUEST call?
另外,人们可以在 HTTP_REQUEST 调用中伪造 REMOTE_ADDR 吗?
回答by Czarek Tomczak
HTTP_ORIGIN
is a way to protect against CSRF(Cross Site Request Forgery) requests. Currently it is implemented only by Chrome (as of Nov 2011). I tested Firefox and Opera, but they failed.
HTTP_ORIGIN
是一种防止CSRF(跨站点请求伪造)请求的方法。目前它仅由 Chrome 实现(截至 2011 年 11 月)。我测试了 Firefox 和 Opera,但都失败了。
Its name in the request header is Origin
. On the server in my PHP script I see it as HTTP_ORIGIN
in the $_SERVER
array. This header is sent only in some cases, when protection against CSRF is required (only POST should be sufficient). Here is list of all requests whether it is set or not:
它在请求标头中的名称是Origin
. 在我的 PHP 脚本中的服务器上,我看到它HTTP_ORIGIN
在$_SERVER
数组中。此标头仅在某些情况下发送,当需要针对 CSRF 进行保护时(仅 POST 就足够了)。以下是所有请求的列表,无论是否设置:
https://wiki.mozilla.org/Security/Origin
https://wiki.mozilla.org/Security/Origin
- Anchor tag - NO
- Window navigation - NO
- IMG - NO
- iframe, embed, applet - YES
- Form (GET and POST) - YES
- SCRIPT - YES
- stylesheets - NO
- dependent loads from stylesheets - NO
- Redirects - YES
- XHR - YES
- 锚标签 - 否
- 窗口导航 - 否
- IMG - 否
- iframe、嵌入、小程序 - 是
- 表单(GET 和 POST) - 是
- 脚本 - 是
- 样式表 - 没有
- 来自样式表的依赖加载 - 否
- 重定向 - 是
- XHR - 是
The Origin
header is implemented only in Chrome, unfortunately. It was announced first in January 2010 on Google Chrome's blog:
Origin
不幸的是,标题仅在 Chrome 中实现。它于 2010 年 1 月在 Google Chrome 的博客上首次宣布:
http://blog.chromium.org/2010/01/security-in-depth-new-security-features.html
http://blog.chromium.org/2010/01/security-in-depth-new-security-features.html
CSRF Protection via Origin Header
The Origin header is a new HTML5 feature that helps you defend your site against cross-site request forgery (CSRF) attacks. In a CSRF attack, a malicious web site, say attacker.com, instructs the user's browser to send an HTTP request to a target server, say example.com, that confuses the example.com server into performing some action. For example, if example.com is a webmail provider, the CSRF attack might trick example.com into forwarding an email message to the attacker.
The Origin header helps sites defend against CSRF attacks by identifying which web site generated the request. In the above example, example.com can see that the request came from the malicious web site because the Origin header contains the value http://attacker.com. To use the Origin header as a CSRF defense, a site should modify state only in response to requests that either (1) lack an Origin header or (2) have an Origin header with a white-listed value.
通过 Origin Header 的 CSRF 保护
Origin 标头是一项新的 HTML5 功能,可帮助您保护站点免受跨站点请求伪造 (CSRF) 攻击。在 CSRF 攻击中,一个恶意网站(例如 attack.com)指示用户的浏览器向目标服务器(例如 example.com)发送 HTTP 请求,从而使 example.com 服务器混淆以执行某些操作。例如,如果 example.com 是网络邮件提供商,CSRF 攻击可能会诱使 example.com 将电子邮件消息转发给攻击者。
Origin 标头通过识别生成请求的网站来帮助站点抵御 CSRF 攻击。在上面的示例中,example.com 可以看到请求来自恶意网站,因为 Origin 标头包含值http://attacker.com。要将 Origin 标头用作 CSRF 防御,站点应仅在响应以下请求时修改状态:(1) 缺少 Origin 标头或 (2) 具有带有白名单值的 Origin 标头。
I am just implementing CSRF protection in my PHP script, I personally use Chrome, so that is sufficient for me, I hope other browsers will catch up with Chrome soon.
我只是在我的 PHP 脚本中实现 CSRF 保护,我个人使用 Chrome,所以这对我来说已经足够了,我希望其他浏览器能尽快赶上 Chrome。
What is funny is that Mozilla invented that security feature, as you can read lots of documentation of that Origin
header on its website, but they still didn't have time to implement it ;-)
有趣的是 Mozilla 发明了该安全功能,因为您可以Origin
在其网站上阅读该标题的大量文档,但他们仍然没有时间实施它;-)
HTTP_ORIGIN
seems to contain only protocol
and domain
, without slash at the end:
"http://www.example.com" - even if you submit the form from "http://www.example.com/myform/".
HTTP_ORIGIN
似乎只包含protocol
and domain
,末尾没有斜线:“ http://www.example.com” - 即使您从“ http://www.example.com/myform/”提交表单。
A simple protection against CSRF in PHP script:
PHP 脚本中针对 CSRF 的简单保护:
if ($_SERVER['REQUEST_METHOD' == 'POST']) {
if (isset($_SERVER['HTTP_ORIGIN'])) {
$address = 'http://' . $_SERVER['SERVER_NAME'];
if (strpos($address, $_SERVER['HTTP_ORIGIN']) !== 0) {
exit('CSRF protection in POST request: detected invalid Origin header: ' . $_SERVER['HTTP_ORIGIN']);
}
}
}
This script could still be upgraded to support PORT other than 80 (Origin contains the port when it's different than 80), HTTPS connections, and submitting the forms from different subdomains (ex. sub.example.com => posting request to www.example.com).
此脚本仍可升级以支持 80 以外的 PORT(Origin 包含不同于 80 的端口)、HTTPS 连接以及提交来自不同子域的表单(例如 sub.example.com => 向 www.example 发布请求.com)。
回答by ceejayoz
HTTP_ORIGIN
is neither sent by all browsers nor is it secure.
HTTP_ORIGIN
既不是由所有浏览器发送也不是安全的。
Nothing sent by the browser can ever be considered safe.
浏览器发送的任何内容都不能被认为是安全的。
回答by Gerard ONeill
People here are thinking about this all wrong -- the 'CORS' standard isn't so the server doesn't get hacked, even if it helps that in addition to what it does. The purpose is to allow 'THE BROWSER' to have a way of easing up on requests that go against the same origin policy. If the client and the server are on the same page, then the 'CLIENT' can decide whether or not to allow the request.
这里的人们认为这一切都是错误的——“CORS”标准并不是为了让服务器不会被黑客入侵,即使它除了它的作用之外还有帮助。目的是允许“浏览器”有一种方法来缓解违反同源策略的请求。如果客户端和服务器在同一页面上,则“CLIENT”可以决定是否允许请求。
Obviously by having the server participate in the decision you are helping in the security process.
显然,通过让服务器参与您在安全过程中帮助的决策。
But it won't protect the server from unauthorized access - that is what passwords and cookies are for.
但它不会保护服务器免受未经授权的访问 - 这就是密码和 cookie 的用途。
The clientcan be (as someone mentioned) a telnet tool, where every single thing crafted is fake.
该客户端可以(有人提及)的telnet工具,在这里的每一件事情制作是假的。
But one of Chrome's, and FF's, etc, selling points is that they will help you by not allowing Javascript to go outside of the same origin sandbox, which means the only thing by default that can be compromised is the stuff that is on the 'attackers' own website. Or other sites that decide to not be secure.
但是 Chrome 和 FF 等的卖点之一是,它们将通过不允许 Javascript 离开同源沙箱来帮助您,这意味着默认情况下唯一可以受到损害的是'攻击者自己的网站。或其他决定不安全的网站。
CORS is the technology that allows you to say -- hey, I want users to be able to consume my snazzy service from the javascript on this other site they use. So I'm gonna add this site to my exceptions. Which means you are helping your authorized users poke a hole in their browser security for that particular site. Which means a hole that a hacker can exploit. Thus the care with which you set up the service, right?
CORS 是一种技术,可以让您说——嘿,我希望用户能够从他们使用的另一个站点上的 javascript 使用我的时髦服务。所以我要把这个网站添加到我的例外中。这意味着您正在帮助您的授权用户在该特定站点的浏览器安全性中戳破一个漏洞。这意味着黑客可以利用的漏洞。因此,您设置服务时的小心心,对吗?
This means that any site that doesn't have CORS set up is by default secure from Cross Site Scripting from a compliant browser (barring bugs and hacks of course). The browser will ask if this service wants to participate in the origin site's javascript, and if the cross site says "I don't know nothing about this damn site", then the browser's javascript engine will close the connection and dump the data.
这意味着任何没有设置 CORS 的站点在默认情况下都是安全的,不受来自兼容浏览器的跨站点脚本的影响(当然,除了错误和黑客攻击)。浏览器会询问这个服务是否要参与源站的javascript,如果跨站说“我对这个该死的站点一无所知”,那么浏览器的javascript引擎会关闭连接并转储数据。
So just to summarize -- CORS doesn't help you make thing secure. It helps you make a hole in your browsers ability to make a user more secure. But hopefully in a managed way.. and only for particular sites..
所以总结一下——CORS 并不能帮助你确保安全。它可以帮助您在浏览器中制造漏洞,使用户更加安全。但希望以一种有管理的方式......并且仅适用于特定站点......
回答by Marc B
HTTP is a plain-text protocol. The ENTIRErequest header/body structure can be faked to say anything you want.
HTTP 是一种纯文本协议。该完成的请求头/车身结构可以伪造说你想要的任何东西。
回答by Sergey Karasev
Upgraded:
升级:
function isOriginAllowed($incomingOrigin, $allowOrigin)
{
$pattern = '/^http:\/\/([\w_-]+\.)*' . $allowOrigin . '$/';
$allow = preg_match($pattern, $incomingOrigin);
if ($allow)
{
return true;
}
else
{
return false;
}
}
$incomingOrigin = array_key_exists('HTTP_ORIGIN', $_SERVER) ? $_SERVER['HTTP_ORIGIN'] : NULL;
$allowOrigin = $_SERVER['HTTP_HOST'];
if ($incomingOrigin !== null && isOriginAllowed($incomingOrigin, $allowOrigin))
{
exit("CSRF protection in POST request: detected invalid Origin header: " . $incomingOrigin);
}
Example:
例子:
- http:// media.mydomain.com TRUE
- http:// offline.mydomain.com TRUE
- http:// domen1.mydomain.com TRUE
- http:// domen_1.mydomain.com TRUE
- http:// domen-1.mydomain.com TRUE
- http:// ololomydomain.com FALSE
- http:// mydomain.com TRUE
- http:// pro.mydomain.com TRUE
- http:// super.pro.mydomain.com TRUE
- http:// super.pro.fakemydomain.com FALSE
- http:// pro.fakemydomain.com FALSE
- http://media.mydomain.com 正确
- http://offline.mydomain.com 真
- http:// domen1.mydomain.com 是
- http:// domen_1.mydomain.com 是
- http:// domen-1.mydomain.com 是
- http://ololomydomain.com 错误
- http://mydomain.com 正确
- http://pro.mydomain.com 正确
- http://super.pro.mydomain.com 真
- http://super.pro.fakemydomain.com 错误
- http://pro.fakemydomain.com 错误
回答by Andy Lester
Everythingin the HTTP request can be faked.
一切都在HTTP请求可以伪造。