同源策略和CORS(跨域资源共享)

时间:2013-02-04 06:12:07

标签: ajax cors cross-domain

我试图了解CORS。根据我的理解,它是一种在浏览器中实现的安全性机制,以避免除了用户打开的域之外的任何ajax请求(在URL中指定)

现在,由于此限制,实施了许多CORS以使网站能够进行跨源请求。但根据我的理解,实施CORS违反了“同源政策”的安全目的 SOP

CORS只是为了提供对哪个请求服务器想要服务的额外控制。也许它可以避免垃圾邮件发送者。

来自Wikipedia

  

要发起跨源请求,浏览器会发送请求   Origin HTTP标头。此标头的值是该网站   服务页面。例如,假设有一个页面   http://www.example-social-network.com尝试访问用户的数据   在online-personal-calendar.com。如果用户的浏览器实现   CORS,将发送以下请求标头:

     

原产地:http://www.example-social-network.com

     

如果online-personal-calendar.com允许请求,它会发送一个   响应中的Access-Control-Allow-Origin标头。的价值   header表示允许的源站点。例如,a   对先前请求的回复将包含以下内容:

     

Access-Control-Allow-Origin:http://www.example-social-network.com

     

如果服务器不允许跨源请求,则浏览器   将传递错误到example-social-network.com页面而不是   online-personal-calendar.com回复。

     

要允许访问所有页面,服务器可以发送以下响应   头:

     

Access-Control-Allow-Origin:*

     

但是,这可能不适用于其中的情况   安全是一个问题。

我在这里缺少什么? CORS保护服务器与保护客户端的意图是什么。

2 个答案:

答案 0 :(得分:80)

同源政策

这是什么?

同源策略是浏览器之间标准化的安全措施。 "来源" 主要是指"域" 。它可以防止不同的来源相互交互,以防止跨站点请求伪造等攻击。

CSRF攻击如何运作?

浏览器允许网站以cookie的形式在客户的计算机上存储信息。这些cookie附带了一些信息,比如cookie的名称,创建时间,过期时间,设置cookie等等.Cookie看起来像这样:

Cookie: cookiename=chocolate; Domain=.bakery.com; Path=/ [// ;otherDdata]

所以这是一个巧克力饼干,应该可以从http://bakery.com及其所有子域访问。

此Cookie可能包含一些敏感数据。在这种情况下,该数据为...... chocolate。你可以看到,非常敏感。

因此浏览器会存储此Cookie。每当用户向可访问此cookie的域发出请求时,cookie将被发送到该域的服务器。快乐的服务器。

这是一件好事。服务器在客户端存储和检索信息的超酷方式。

但问题是,这允许http://malicious-site.com将这些Cookie发送到http://bakery.com,而无需用户知道!例如,请考虑以下情形:

# malicious-site.com/attackpage

var xhr = new XMLHttpRequest();
xhr.open('GET', 'http://bakery.com/order/new?deliveryAddress="address of malicious user"');
xhr.send();

如果您访问恶意网站,并执行上述代码,并且不存在同源政策,则恶意用户会代表您下订单,并在他的位置获取订单......您可能不喜欢这个。

之所以发生这种情况是因为您的浏览器已将巧克力Cookie发送至http://bakery.com,这使http://bakery.com认为正在请求新订单,明知< / em>的。但你不是。

简而言之,就是CSRF攻击。跨网站提出了伪造请求。 &#34;跨站点请求伪造&#34;。由于同源政策,它不会起作用。

同源政策如何解决这个问题?

它阻止malicious-site.com向其他域发出请求。简单。

换句话说,浏览器允许任何网站向任何其他网站发出请求。它可以防止不同的起源通过这样的请求相互交互,比如AJAX。

但是,来自其他主机的资源加载,例如图片,脚本,样式表,iframe,表单提交等,不受此限制。我们需要另一面墙来保护我们的面包店免受恶意网站的攻击,使用CSRF Tokens

CSRF代币

如上所述,恶意网站仍然可以在不违反同源策略的情况下执行此类操作:

<img src='http://bakery.com/order/new?deliveryAddress="address of malicious user"'/>

浏览器将尝试从该网址加载图片,从而向该网址发送GET请求,发送所有Cookie。为了阻止这种情况发生,我们需要一些服务器端保护。

基本上,我们将适当熵的随机唯一标记附加到用户的会话中,将其存储在服务器上,并将其与表单一起发送给客户端。提交表单时,客户端会将该令牌与请求一起发送,服务器会验证该令牌是否有效。

既然我们已经这样做了,并且恶意网站再次发送请求,它将始终失败,因为恶意网站没有可行的方法来知道用户会话的令牌。


CORS

如果需要,可以在需要跨站点请求时规避策略。这称为 CORS 。跨源资源共享。

这是通过拥有&#34;域&#34;告诉浏览器冷静,并允许这样的请求。这&#34;告诉&#34;可以通过传递标题来完成。类似的东西:

Access-Control-Allow-Origin: //comma separated allowed origins list, or just * 因此,如果http://bakery.com将此标头传递给浏览器,并且创建对http://bakery.com的请求的页面出现在原始列表中,则浏览器会将请求与Cookie一起发送。

根据这些规则定义起源 1 。例如,同一域的不同端口不是同一个源。因此,如果端口不同,浏览器可能会拒绝此请求。与往常一样,我们的亲爱的 Internet Explorer是例外。 IE以相同的方式处理所有端口。这是非标准没有其他浏览器以这种方式运行。 不要依赖此


JSONP

带有填充的JSON只是一种绕过同源策略的方法,当CORS不是一个选项时。这是冒险的,也是一种不好的做法。避免使用它。

这项技术涉及的是向其他服务器发出如下命令:

<script src="http://badbakery.com/jsonpurl?callback=cake"></script>

由于同源策略不会阻止此 2 请求,因此该请求的响应将被加载到页面中。

此网址很可能会回应JSON内容。但只是在页面上包含JSON内容并不会有帮助。它会导致错误,当然。因此http://badbakery.com接受一个回调参数,并修改JSON数据,将其包装在传递给回调参数的任何内容中。

所以不是回来,而是

{ user: "vuln", acc: "B4D455" }

这是无效的JavaScript抛出错误,它会返回,

cake({user: "vuln", acc:"B4D455"});

是有效的JavaScript,它会被执行,并且可能根据cake函数存储在某处,以便页面上的其余JavaScript可以使用这些数据。

这主要由API用于将数据发送到其他域。同样,这是一种不好的做法,可能存在风险,应该严格避免。

为什么JSONP不好?

首先,它非常有限。如果请求失败,您将无法处理任何错误(至少不是以理智的方式)。您无法重试请求等

它还要求您在全局范围内拥有cake功能,这不是很好。如果您需要使用不同的回调执行多个JSONP请求,厨师可以保存您。这可以通过各种图书馆的临时功能来解决,但仍然是一种做事情的hackish hackish。

最后,您在DOM中插入随机JavaScript代码。如果您不能100%确定远程服务将返回安全蛋糕,则您无法依赖此。


参考

1。 https://developer.mozilla.org/en-US/docs/Web/Security/Same-origin_policy#Definition_of_an_origin

2。 https://www.w3.org/Security/wiki/Same_Origin_Policy#Details

其他有价值的读物

  

http://scarybeastsecurity.blogspot.dk/2009/12/generic-cross-browser-cross-domain.html

     

http://tools.ietf.org/html/rfc3986(抱歉:p)

     

https://developer.mozilla.org/en-US/docs/Web/Security/Same-origin_policy

     

https://www.owasp.org/index.php/Cross-Site_Request_Forgery_(CSRF)

答案 1 :(得分:5)

同源策略(SOP)是策略浏览器通过跨站点脚本(XSS)防止漏洞的实现。这主要是为了保护服务器,因为很多时候服务器可以处理身份验证,cookie,会话等。

跨源资源共享(CORS)是放松SOP的少数几种技术之一。由于默认情况下SOP处于“打开”状态,因此即使请求是从其他域发送的,在服务器端设置CORS也会允许通过XMLHttpRequest将请求发送到服务器。如果您的服务器旨在提供来自其他域的请求(例如,如果您提供API),则此功能非常有用。

我希望这可以清除SOP和CORS之间的区别以及每种方法的目的。