0

i have got a problem with socket IO connection from the page, witch geneerated by nodeJs server, to another nodeJs server listening by Socket.IO

The idea is contains of 2 tasks: Generating HTML templates by one Express server Support socket io by another express server

Here is server.js code:

const app = require('express');
const util = require('util');
const http = require('http');
const fs = require('fs');
const debug = console.log;
const moment = require('moment');
const event = require('events').EventEmitter;
var server = app();
server.use(function (req, res, next) {
        res.setHeader('Access-Control-Allow-Origin', '*');
        res.setHeader('Access-Control-Allow-Methods', 'GET, POST, OPTIONS, PUT, PATCH, DELETE');
        res.setHeader('Access-Control-Allow-Headers', 'X-Requested-With,content-type');
        res.setHeader('Access-Control-Allow-Credentials', true);
        next();
    }
);
server.use(app.json());
server.use(app.urlencoded());
server.use(app.logger());
server.use(app.favicon());
server.use(app.static(__dirname + '/core'));
server.get('*', function (req, res, next) {
    debug('Connection refused: \t' + req.url);
    var r = (e.url.split('/')[2] == 'socket.io.js') ? server.st.socket : server.st.tmp; // Return TMP-HTML FILE OR SOCKET.IO JS FILE FOR CLIENT
    res.send(r);
    res.end();
});
server.st = {
        socket: fs.readFileSync('./socket.io.js', 'utf-8')
        tmp: fs.readFileSync('./tmp.html', 'utf-8')
}
server.listen(81);
*******************************************************************************
//Creating SOCKET server
    io = require('socket.io').listen(82);
    io.configure(function () {
        io.set('log level', 1);
        io.set('origin', '*');
    });
    io.sockets.on('connection', function (socket) {
        debug('IT IS WORK')
    })

Here Is tmp.html code:

<!DOCTYPE html>
<html>
<head>
    <script src="/socket.io/socket.io.js"></script>
    <script>
        var socket = io.connect('http://localhost:82');
    </script>
</head>
<body>
</body>

And default Socket.io.js for client

And here is Error on client side

XMLHttpRequest cannot load http://localhost:82/socket.io/?EIO=2&transport=polling. No 'Access-Control-Allow-Origin' header is present on the requested resource. Origin 'http://localhost:81' is therefore not allowed access. 

What's wrong with this *?

tshepang
  • 12,111
  • 21
  • 91
  • 136
user2996204
  • 51
  • 1
  • 3

2 Answers2

5

The answer was:

HTTP server that must support socket, has default origin settings in stock Socket options, that can not be changed by var IO configurate, manager.js in 778 line (v0.9), you must write in origin options something like this: headers['Access-Control-Allow-Origin'] = '*'; OR

The best way of the solution is:

HTTP server that must support socket, has binded address with it's own listener, that creates a socket beetwen client that request this tunnel, using socket.io.js file, that i get from localhost:81.. That's why i asked my self: "why i get socket client file from server, that irrelevanted to socket server?" And changed

<script src="http://localhost:82/socket.io/socket.io.js"></script>
<script>
    var socket = io.connect('http://localhost:82');
</script> 

And it works. THX, with great love from Russia. Bye.

user2996204
  • 51
  • 1
  • 3
0

You are creating express socket using port 81, and then creating another socket for socket.io on port 82, and then from front-end you are trying to load socket.io.js from express while it is not serving it (you should bind socket.io to same server as express), and then you are trying to connect to http protocol to port 82 - which is considered as another domain, and will fail for CORS.

Do not try to bang-in code by pieces and expect it to work, you have to understand what it does, before you can use it, otherwise you wont get far.

Please follow examples of socket.io on official website for express: http://socket.io/#how-to-use

UPDATE: based on your mention of requirements in comments, that you need another domain, you might need to check other 2 options: proxying WS traffic from domain that serves htmls or use alternatives that do good job with CORS, like SockJS.

moka
  • 22,846
  • 4
  • 51
  • 67
  • But this is the whole point. I need 2 web servers. One for generating Templates and rendering static files. Second one must support web socket, witch must work for all connections with any other domains. – user2996204 Feb 19 '14 at 09:01
  • http://socket.io/#how-to-use and this one i read many times, but the answer is not there – user2996204 Feb 19 '14 at 09:03
  • The main probles is that [link](http://enable-cors.org/server_expressjs.html), but when use stock HTTP module for createServer() from "io = require('socket.io').listen(82);" with setting origin : '*'; there is no reaction to CORS. But if create server manuly, with requestListener AS express app, it works great, But socket.io doest not listen IT. – user2996204 Feb 19 '14 at 09:08
  • And more over. I'm working with node since it was 0.6 version – user2996204 Feb 19 '14 at 09:26
  • Due to security and enforcements you will not be able to make WS connection from one domain to another - browsers will not allow that regardless of headers. You might want to check other options: proxying WS on same domain, or check SockJS which is meant to work with CORS out of the box: https://github.com/sockjs/sockjs-node – moka Feb 19 '14 at 13:33