我花了很长时间尝试将Socket.IO-Client连接到运行在Sails.js框架上的服务器。客户端基本上是一个在Raspberry Pi上运行Node.js的简单JavaScript应用程序。
这个想法是一个简单的设备连接到服务器,服务器然后注册设备并订阅它以获取消息。设备从服务器接收消息并执行某些操作。我不希望客户端依赖于任何框架,因此,我试图避免使用Sailsjs-socket.io-client。目前,服务器和客户端都在我的本地计算机上运行。这是代码:
// Server side. Sails.js. DevicesController.js
module.exports = {
handshake: function (req, res) {
if (!req.isSocket) return res.badRequest();
Devices.create({}).exec(function (error, data) {
Devices.subscribe(req.socket, data);
});
return res.ok();
}
};
// Client side
var socket = require('socket.io-client')('http://localhost:1337/devices/handshake');
socket.on('error', function(e) {
console.log(e);
// Here I get 'Invalid namespace'
});

因此,我收到错误'无效的命名空间'在客户端,如果我是对的,这意味着服务器没有' / devices / handshake'打开。但是,在服务器端,如果我列出现有的房间ID(sails.sockets.rooms()),我可以看到,当客户端尝试连接到服务器时,总是会创建一个新房间。
我尝试连接到' / devices / handshake'从浏览器下面的javascript,显然它工作。它显然可以运行Sailsjs-socket.io-client。
io.socket.get('/devices/handshake', function (data, jwres) {
console.log(jwres);
});
io.socket.on('devices', function (data, jwres) {
console.log(data);
});

任何想法我做错了什么?
答案 0 :(得分:5)
这里看起来很混乱:Socket.io名称空间,Socket.io路径和Sails路由。通过浏览Socket.io docs,您可以了解前两个方面的更多信息。关于Sails,要记住的主要事情是仅侦听默认/
命名空间上的连接;因此,您应始终将客户端套接字连接到:
var socket = require('socket.io-client')('http://localhost:1337');
将/devices/handshake
添加到末尾不会更改套接字尝试连接的URL;它总是会尝试连接到http://localhost:1337/socket.io
。相反,它意味着它将尝试使用/devices/handshake
命名空间注册套接字,Sails没有提供。
另一方面,当您调用io.socket.get('/devices/handshake')
时,您正在使用Sails套接字客户端库向您应用中的路由发出虚拟请求,就像您' d使用AJAX(例如jQuery中的$.get('/devices/handshake')
)。这正是创建sails.io.js
的原因 - 它使这种事情变得非常容易!它也没有真正把你绑在前端;所有sails.io.js
都提供了一些包装器,以便通过套接字轻松与Sails后端进行通信。在幕后,io.socket.get
只是使用Socket.io-client .emit()
方法向服务器发送get
事件,其中有效负载描述了Sails操作的URL和参数。跑。所以,这个:
io.socket.get('/devices/handshake', function(body, res){...})
相当于连接自己的套接字并执行此操作:
socket.emit('get', {url: '/devices/handshake'}, function(res){...})
首次连接时为套接字运行逻辑的推荐方法是允许套接字在客户端上完全连接,然后从客户端向服务器发出请求(正是您在第二个代码中执行的操作)块)。要详细了解此背后的原因,请参阅this note in the Sails 0.11.x migration guide。该说明还解释了如果由于某种原因必须在服务器连接时立即运行逻辑,则可以执行
sails.io.on('connect', function (newlyConnectedSocket){})
在你的引导功能(config/bootstrap.js
)中。