5

I'm having cross domain configuration issues using nginx and sails. The problem is that if I get the socket to connect properly via http://domain-server.com/socket.io/ then the RESTful request will fail. If RESTful works the socket will not.

Setup

Client http://domain.com

Server http://server-domain.com

Client is an angular application using "sails.io.js": "0.10.3" and this config io.sails.url = 'http://domain-server.com';.

Server is a sails application with both RESTful request and socket features.

Sails CORS config

module.exports.cors = {
    allRoutes: true,
    origin: 'http://domain.com',
    credentials: true,
    methods: 'GET, POST, PUT, DELETE, OPTIONS, HEAD',
    headers: 'content-type,Access-Control-Allow-Origin'
};

Sails socket config

module.exports.socket {
    onConnect: function() {},
    onDisconnect: function() {},
    authorization: false,
    'backwardsCompatibilityFor0.9SocketClients': false,
    grant3rdPartyCookie: true,
    origins: 'http://domain.com'
};

nginx config

Commented out are what I've fiddled with in the nginx configuration without much success (also tried the client address instead of *).

server {
    listen 80;

    server_name domain-server.com;
#add_header Access-Control-Allow-Origin *;
    location / {
#       add_header Access-Control-Allow-Origin *;

        proxy_pass http://localhost:1337;
        proxy_http_version 1.1;
        proxy_set_header Upgrade $http_upgrade;
        proxy_set_header Connection 'upgrade';
        proxy_set_header Host $host;
#        proxy_set_header Access-Control-Allow-Origin *;
        proxy_cache_bypass $http_upgrade;
   }
}

angularjs service method making the RESTful calls

function query(path, attributes) {

    return $http({
        url: domain + path,
        params: attributes,
        method: "GET",
        widthCredentials: true
    });
}

In the angular config function

$httpProvider.defaults.useXDomain = true;

It is the current configuration and here are the results I am experiencing.

Browser console output

Resource interpreted as Script but transferred with MIME type text/html: "http://domain-server.com/__getcookie". - Good

|>
\___/ sails.io.js:200 io.socket connected successfully.
- Good

XMLHttpRequest cannot load http://domain-server.com/login?password=test&username=test. No 'Access-Control-Allow-Origin' header is present on the requested resource. Origin 'http://domain.com' is therefore not allowed access. - Not good

UPDATE

It seems like everything works wonder if I start sails directly using sails lift or node app.js yet when starting it using the upstart script in a .conf file the cross domain issue occurs.

upstart script

#!upstart
description "demo"
author "gillesc"

start on (local-filesystems and net-device-up IFACE=eth0)
stop on shutdown

respawn
respawn limit 5 60

script
  exec /usr/bin/node /var/www/apps/domain-server.com/app.js > /var/www/apps/domain-server.com/server.log 2>&1
end script
GillesC
  • 10,647
  • 3
  • 40
  • 55
  • Where is this hosted? Certain cloud hosts (like OpenStack) seem to block CORS headers from being sent. – sgress454 Aug 29 '14 at 17:56
  • I can get the CORS to work fine for RESTful, it just when they do the socket.io side of thing no longer work. Sounds like there is a conflict somewhere. – GillesC Aug 29 '14 at 21:38
  • What do you get if you navigate to `http://domain-server.com/login?password=test&username=test` in the browser? Is it an nginx error page? Are you reverse proxying requests properly from nginx to the sails application? Or are they on different ports? – david Aug 31 '14 at 10:43
  • @david I'm getting `Not Found`, from nginx I think as the 404 sails view is just the string `404`. – GillesC Aug 31 '14 at 11:16
  • Yeah, it sounds like you're serving the sails app and the websocket from the same port. Either switch the websocket over to a different port or decide which urls should go to which and set up nginx. – david Aug 31 '14 at 11:51
  • Theoretically you should be able to run socket.io and a webserver on the same port: http://stackoverflow.com/a/5969772/867294, but maybe nginx doesn't like it. Can you visit: `http://localhost:1337/login?password=test&username=test` directly? do you still get the 404 ? Are any CORS headers present ? If rest is working, I don't think you should try to modify any CORS headers from nginx – Willem D'Haeseleer Aug 31 '14 at 12:35
  • Removing the socket configuration make that works all the time. For the REST calls I noticed something weird, if I start the application using `sails lift` or even `node app.js` manually it works perfectly. If I use `start server-name` the cross domain issue occur. I'll update my question with the upstart script. – GillesC Aug 31 '14 at 12:45

1 Answers1

1

Try adding the following to the top of your Sails app's app.js file:

process.chdir(__dirname);

The not found you're seeing is likely the default Express 404 message. If you try to lift a Sails app outside of its own directory, the API files (e.g. controllers) won't get loaded properly. The process.chdir was added to the default app.js at some point to prevent this problem, but it looks like there was a regression somewhere along the way.

sgress454
  • 24,870
  • 4
  • 74
  • 92