Cross-Origin Resource Sharing (CORS)
CORS is a mechanism that allows browser scripts on pages served from other domains (e.g. myothersite.com) to talk to your server (e.g. api.mysite.com). Like JSONP, the goal of CORS is to function as a secure method to circumvent the same-origin policy; allowing your Sails server to successfully respond to requests from client-side JavaScript code running on a page from some other domain. But unlike JSONP, it works with more than just GET requests.
Sails can be configured to allow cross-origin requests from a list of domains you specify, or from every domain. This can be done on a per-route basis, or globally for every route in your app.
Enabling CORS
For security reasons, CORS is disabled by default in Sails. But enabling it is dead-simple.
To allow cross-origin requests from any domain to any route in your app, simply enable allRoutes
in config/cors.js
:
allRoutes: true
See sails.config.cors
for a comprehensive reference of all available options.
Configuring CORS For Individual Routes
Besides the global CORS configuration, you can set up individual routes in config/routes.js
to accept (or deny) cross-origin requests. To indicate that a route should accept CORS requests using the configuration parameters in config/cors.js
, set its cors
property to true
:
"get /foo": {
controller: "FooController",
action: "index",
cors: true
}
If you have the allRoutes
parameter set to true
in config.cors.js
, but you want to exempt a specific route, you can do so by explicitly setting its cors
property to false
:
"get /foo": {
controller: "FooController",
action: "index",
cors: false
}
To override specific CORS configuration parameters for a route, add a cors
property object:
"get /foo": {
controller: "FooController",
action: "index",
cors: {
origin: "http://sailsjs.org, http://sailsjs.com",
credentials: false
}
}
Security Levels
By default, Sails will still process all the requests that come in regardless of domain, even with CORS enabled: it will simply set the appropriate headers on the response so that the client can decide whether or not to show the response. For example, if you send a GET
request to /foo/bar
from a domain that is not in your CORS whitelist, the bar
action in your FooController.js
file will still run, but the browser will throw away the result. This may seem counterintuitive, but it is important because it allows non-browser-based clients (like Postman and curl) to work while still blocking the kind of attacks that the Same-Origin Policy is meant to protect against.
If you want to completely prevent Sails from processing requests from disallowed domains, you can use the securityLevel
setting:
module.exports.cors = {
allRoutes: true,
origin: "http://sailsjs.org",
securityLevel: 1
}
Security level 1 (high) will respond with a 403 status code to any request from a disallowed origin prefixed with the http
or https
protocol. Security level 2 (very high) will do the same, but extended to all protocols (so things like Postman and curl won't work).