70

I am trying to understand CORS. From my understanding, it empowers you to limit which domains can access a resource on your server. However, this doesn't seem like the full story. For example, I have a web service without CORS enabled. I cannot hit this web service from my web application via jQuery (the app is running on localhost). However, I can hit the web service from Postman. So, I'm a bit confused. Is there some extra client side work that involves CORS?

Some User
  • 3,779
  • 8
  • 39
  • 75

2 Answers2

101

The server is responsible for reporting the allowed origins. The web browser is responsible for enforcing that requests are only sent from allowed domains.

CORS is applied to requests when an Origin header is included in the request. This includes requests made from JavaScript and POST requests. It's not applied all resources. The origin is the protocol, host and port that is making the request. Requests made by JavaScript use the origin that loaded the JavaScript, not the origin that it was loaded from.

When CORS is not enabled a browser will rely on the same origin policy. The same origin policy is only applied to scripts. The browser will only allow scripts to be loaded from same origin as the loaded page. The same origin policy is assumed when not origins are explicitly allowed.

An HTTP client other than a browser won't use either the same origin policy or CORS. Requests made from these other HTTP clients don't have an origin. Unless the Postman desktop app emulates a browser it will be able to make requests to any URL.

CORS and the same origin policy are needed because a browser does not implicitly trust the websites it visits to make requests to other websites. They don't protect the origin site, they protect the site receiving the cross origin requests. This is why the allowed origins are up to the targeted server.

Without these policies a simple script that repeatedly loads a website could be distributed by ad networks or script injection and then any browser loading the script would contribute to a denial of service attack on the website. With CORS and the same origin policy a browser will limit the impact of this script.

Another important protection CORS provides is to protect against Cross-site request forgery. It prevents a site from making some types of requests to another site. These requests would be made using any previously created tokens, such as session tokens.

CORS by example:

A web browser loads a page from www.example.com. The page includes a script that makes a request to www.example.org. The origin of the request is www.example.com. The browser either makes the request or sends an OPTIONS request first (the preflight request). When the server at www.example.org receives a request from an origin other than www.example.org it responds with a response header Access-Control-Allow-Origin which tells the browser the origins allowed to make requests. It may also respond with other headers like Access-Control-Allow-Methods and Access-Control-Allow-Headers that can restrict the types of allowed requests. When the browser is told what origins are allowed it will block future requests from disallowed origins.

Matt Champion
  • 2,155
  • 1
  • 9
  • 12
  • 2
    Is CORS a security thing then? I have a hard time viewing it as a security component if its the web browser's responsibility to enforce that that request are only sent from allowed domains. – Some User Apr 30 '16 at 22:41
  • 8
    @ZachTempleton CORS is a way to relax the same origin policy. The same origin policy is used because browsers don't trust the sites they visit or the content they load. It prevents one site from maliciously interfering with another site. – Matt Champion May 01 '16 at 14:34
  • So the main purpose is to secure servers from DoS attacks coming from browsers? – jpenna Feb 18 '19 at 09:38
  • 1
    @jpenna no it also helps prevent cross-site request forgery attacks. If a site uses a cookie to authenticate without the same origin policy injected scripts could make requests using that authentication https://medium.com/@electra_chong/what-is-cors-what-is-it-used-for-308cafa4df1a – Matt Champion Feb 19 '19 at 11:09
  • 3
    Yes, I'm also having a hard time seeing this as security. What if I just write my own web-browser and I just ignore the CORS headers? – redigaffi Apr 25 '19 at 11:10
  • Regarding denial of service — in what cases will the browser preemptively block identical AJAX requests after an initial CORS violation? I just tested this scenario and it didn't seem to be the case. Also, CORS is only enforced for AJAX, but not page elements ` – Peter Sep 02 '19 at 23:25
  • 3
    @redigaffi, then nobody would use that browser :) — but you don't actually have write your own (https://stackoverflow.com/questions/3102819/disable-same-origin-policy-in-chrome). The thing is, it would be extremely dangerous/negligent to log into your bank account using a browser that it is not respecting the same-origin policy. The browser is loading "random" scripts from all over the internet, and without the same-origin policy in effect those scripts could compromise the information that you have entrusted to your browser. – Peter Sep 03 '19 at 00:05
  • I am new and confused with this. What if example.org guy embeds script in web page that makes request to example.org and the same guy also sets cors enabled on example.org? – Yusuf Jul 15 '20 at 19:34
  • When an example.org page makes a request to example.org the origin is the same as the request so no CORS rules are applied. The Access-Control-Allow-Origin header is ignored – Matt Champion Sep 03 '20 at 16:39
12

It's a bit of both actually. Your browser will prevent CORS requests unless the origin of the request (i.e the referrer URL domain) is in a white list on the destination, or the destination approves all requests regardless of origin.

In both cases, the required header (Access-Control-Allow-Origin) is added which tells the browser that it's ok to send the request to the destination.

This ensures that people with malicious intent cannot send requests to another domain without the the user knowing about it.

John Mc
  • 2,761
  • 1
  • 20
  • 34
  • 1
    What do you mean by "This ensures that people with malicious intent cannot send requests to another domain without the the user knowing about it"? The malicious person could set their own server with CORS enabled and send the users information there, using XSS for example, and the user would never know. – jpenna Feb 18 '19 at 09:36
  • Yes but you would have to load a compromised website for that to happen. CORS isn't a magic pill that prevents everything but it is a mitigation to XSS – John Mc Feb 19 '19 at 10:07