我有以下代码服务器端。
var io = require('socket.io').listen(8080);
io.sockets.on('connection', function (socket) {
socket.on('event', function(data){
// process...
});
});
客户端(部分)
socket.emit('event', {type:'command', data:'data....'});
for (var i=0; i<=9999999; i++){
socket.emit('unknownEvent', {'type':'attack', data:'a34tagfa3wtasfd'});
}
现在,如何处理和防御'unknownEvent'事件......?..
答案 0 :(得分:3)
更老的问题,但遇到了类似的事情,所以我想我会分享一种方法来做到这一点。
因此,在客户端上,不要将事件作为第一个发出的参数传递,而是使用通用事件名称,如event
或其他东西。我最终使用了应用程序的名称,因为它很短。然后在数据对象中,传入要调用的函数的名称。
所以这个:
socket.emit('awesomeSocketEvent', {hello: 'world'});
成为:
socket.emit('genericEvent', {event:'awesomeSocketEvent', hello:'world'});
重写客户端上的所有内容很糟糕,而我的客户端主要只是emit
- 所以我将socket.io客户端包装在另一个对象中,并使用它自己的emit事件来完成事件名称和数据的更改对象。
现在在服务器端,只有一个名为genericEvent
的自定义事件,因此自定义事件需要重新构建为对象的属性。一旦发生这种情况,可以通过简单的检查来查看对象中是否存在事件,如果有,则调用它,如果不存在,则执行其他操作。
io.sockets.on('connection', function (socket) {
var events = {
awesomeSocketEvent: function(data){
// do your socket stuff here
}
};
socket.on('genericEvent', function(data){
if(data.event in events){
events[data.event](data);
} else {
// do your unknown event stuff here
}
});
});
在编写该部分时查看代码后,我不确定在connect事件中声明事件对象的性能。最好在连接事件之外声明events
,然后将socket
传递给所有函数。
答案 1 :(得分:0)
正如Gntem所说,如果服务器端的Socket.io没有注册的事件处理程序,那么事件将只返回,没有任何东西可以处理它。
如果您正在寻找更多保护(例如,您希望某人使用未注册的事件向您发送垃圾邮件),您可以考虑使用中间件检查事件名称是否有效(或测试其他质量)。像这样:
const socketChecker = {
someEvent:true,
}
io.on('connection', function(socket) {
socket.use((packet, next) => {
if(socketChecker[packet[0]] === true){
next()
} else {
//Disconnect user here
}
});
socket.on('someEvent',function(){
//do work here
})
});
请注意,如果这样做,您将读取可能具有保留名称的数据包(如心跳,连接,消息,json等)。
以下是数据包的参考: http://gevent-socketio.readthedocs.io/en/latest/packet.html
请注意,我实际上并没有使用它,因此我不知道可能会出现什么问题。我只是检查了一些数据包中事件名称的位置。应该找到进一步的文档(或者应该进行更多测试),了解这些数据包内部的实际情况。
答案 2 :(得分:-1)
如果客户端或服务器端Socket.io
没有该事件的注册处理程序,那么它将无法处理它,这意味着它将返回并执行任何操作。
但是如果客户端向服务器发送未注册的事件,您可以始终在客户端或服务器端使用message
事件来接收每条消息。
socket.on('message',function(m){console.log(m);});