CORS With Wildcard Subdomains Using Nginx
This was originally posted on the SHIFT developers blog.
First off - what is CORS? CORS is a means of allowing cross site requests. You can read up in lengthy detail on it’s features here. Simply put, it lets you be on one domain, and perform XMLHttpRequests to another, which is normally not allowed due to the Same Origin Policy.
The domains that may hit your server must be specified in your configuration. You are allowed to use a blanket wildcard, but if you’re allowing cookie sharing, you’re even more restricted in that you need to specify exact domains and wildcards are not allowed. But what if you want to allow *.yoursweetdomain.com? It turns out that’s not supported by the spec, but you can, with some trickery, make it happen. Here’s an example of an nginx server config allowing CORS from any subdomain of yoursweetdomain.com:
server {
root /path/to/your/stuff;
index index.html index.htm;
set $cors "";
if ($http_origin ~* (.*\.yoursweetdomain.com)) {
set $cors "true";
}
server_name yoursweetdomain.com;
location / {
if ($cors = "true") {
add_header 'Access-Control-Allow-Origin' "$http_origin";
add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS, DELETE, PUT';
add_header 'Access-Control-Allow-Credentials' 'true';
add_header 'Access-Control-Allow-Headers' 'User-Agent,Keep-Alive,Content-Type';
}
if ($request_method = OPTIONS) {
return 204;
}
}
}
You can match any regular expression you’re interested in, not just domains, but for simplicity’s sake, that’s what I’m showing. The server will return in it’s header the same server that the request originated, and only if it matches the regex. It’s currently broken out to use a if statement
and a set
, because it’s easier to work with if you want to potentially match on multiple rules.
In figuring all this out this gist proved to be extremely helpful.
If you found this post helpful, please consider sharing to your network. I'm also available to help you be successful with your distributed systems! Please reach out if you're interested in working with me, and I'll be happy to schedule a free one-hour consultation.