Socket.io – Access-Control-Allow-Origin不允许的来源

我知道在这个话题上有一些讨论,但是我不能find我的问题的答案。 我在localhost:8020上的Aptana服务器上运行了一个网页。 在页面上的JavaScript正在击中我已经在本地主机上运行的节点服务器:1337。 这是节点代码:

var io = require('socket.io'); var http = require('http'); var sys = require('sys'); var json = []; var server = http.createServer(function (req, res) { var headers = {}; headers["Access-Control-Allow-Origin"] = "*"; headers["Access-Control-Allow-Methods"] = "POST, GET, PUT, DELETE, OPTIONS"; headers["Access-Control-Allow-Credentials"] = true; headers["Access-Control-Max-Age"] = '86400'; // 24 hours headers["Access-Control-Allow-Headers"] = "X-Requested-With, Access-Control-Allow-Origin, X-HTTP-Method-Override, Content-Type, Authorization, Accept"; res.writeHead(200, headers); res.end(); }); server.listen(1337, '127.0.0.1'); console.log('Server running at http://127.0.0.1:1337/'); var socket = io.listen(server); socket.on('connection', function(){ console.log("Connected"); }); 

我正在处理Cors请求,通过更改标题,我一直在做。 我的客户端代码通常是socket.io初学者的东西。 这里是我的代码标签:

 <script src="http://cdn.socket.io/stable/socket.io.js"></script> <script> // Create SocketIO instance var socket = new io.Socket('localhost',{ port: 1337 }); socket.connect(); // Add a connect listener socket.on('connect',function() { log('<span style="color:green;">Client has connected to the server!</span>'); }); // Add a connect listener socket.on('message',function(data) { log('Received a message from the server: ' + data); }); // Add a disconnect listener socket.on('disconnect',function() { log('<span style="color:red;">The client has disconnected!</span>'); }); // Sends a message to the server via sockets function sendMessageToServer(message) { socket.send(message); log('<span style="color:#888">Sending "' + message + '" to the server!</span>'); } // Outputs to console and list function log(message) { var li = document.createElement('li'); li.innerHTML = message; document.getElementById('message-list').appendChild(li); } 

当我运行的代码,我不断得到“XMLHTTPRequest …原始不允许的访问控制,允许来源”的错误。 我的浏览器是铬。 1.为什么我的浏览器使用XMLHTTPRequest而不是WebSocket? 2.当我更改标题时,为什么会出现Access控制错误? 感谢所有的帮助提前。

实际上,您的自定义标头永远不会写入与socket.io相关的请求。

Socket.IO重写了http服务器的一些方法。 其中之一就是触发'请求'处理程序。 Socket.IO只允许自己成为所有请求的主要处理程序。 然后它testing请求是否实际上是一个socket.io请求(基于请求的path的前缀)。 如果它确定它不应该处理给定的请求,则会触发其他“请求”处理程序。

你可以通过在你的writeHead调用之前放一个console.log语句来看到,你会发现在stdout中没有任何东西出现。

读取源代码 ,似乎socket.io会自动设置一个Access-Control-Allow-Origin标头,并使用请求的origin标头的值。 我会假设有一种方法可以在客户端上设置这样的头文件。

所以,清理一下:

1您的浏览器返回到xhr-polling,因为它不支持websocket或websocket传输失败

2您自己在httpServer request事件中设置的标头永远不会被发送,因此它们对源策略没有任何操作。

解决scheme:find一种方法来设置请求的origin 。 在浏览客户端代码后,我发现没有证据表明这可以轻松完成。

有一点需要注意的是,当Access-Control-Allow-Credentials为true时,不能在Access-Control-Allow-Origin头中使用'*'值。 请删除Access-Control-Allow-Credentials标头,或将Access-Control-Allow-Origin设置为请求Origin标头的值。

根据socket.io文档,你应该能够设置传输的优先级(也许可以跳过一个,如果它产生问题),并直接configurationsocket.io起源。

  io.set('transports', ['websocket', 'xhr-polling', 'jsonp-polling', 'htmlfile', 'flashsocket']); io.set('origins', '*:*');