Socket.io 客户端:使用一个处理程序响应所有事件?

IT技术 javascript events socket.io
2021-03-06 11:07:18

是否可以让 socket.io 客户端响应所有事件而不必单独指定每个事件?

例如,这样的事情(现在显然行不通):

var socket = io.connect("http://myserver");

socket.on("*", function(){
  // listen to any and all events that are emitted from the
  // socket.io back-end server, and handle them here.

  // is this possible? how can i do this?
});

我希望在客户端 socket.io 代码接收到任何/所有事件时调用此回调函数。

这可能吗?如何?

6个回答

socket.io-client 1.3.7更新解决方案

var onevent = socket.onevent;
socket.onevent = function (packet) {
    var args = packet.data || [];
    onevent.call (this, packet);    // original call
    packet.data = ["*"].concat(args);
    onevent.call(this, packet);      // additional call to catch-all
};

像这样使用:

socket.on("*",function(event,data) {
    console.log(event);
    console.log(data);
});

没有一个答案对我有用,尽管 Mathias Hopf 和 Maros Pixel 中的一个很接近,但这是我调整后的版本。

注意:这只捕获自定义事件,而不是连接/断开连接等

不幸的是,不能使用“user.*”; 之类的东西。也许我可以设法实施它。
2021-05-05 11:07:18
嗨,非常好,但是如果您能提供一些输出示例可能会有所帮助^^ 我觉得我需要运行代码才能理解您的答案:)
2021-05-10 11:07:18
谢谢,这有助于我调试丢失的事件!
2021-05-13 11:07:18

看起来 socket.io 库将这些存储在字典中。因此,不要认为不修改源就不可能做到这一点。

来源

EventEmitter.prototype.on = function (name, fn) {
    if (!this.$events) {
      this.$events = {};
    }

    if (!this.$events[name]) {
      this.$events[name] = fn;
    } else if (io.util.isArray(this.$events[name])) {
      this.$events[name].push(fn);
    } else {
      this.$events[name] = [this.$events[name], fn];
    }

    return this;
  };
2021-04-21 11:07:18
在 2019 年,我认为情况不再如此。
2021-05-12 11:07:18

最后,有一个名为socket.io-wildcard的module,它允许在客户端和服务器端使用通配符。

var io         = require('socket.io')();
var middleware = require('socketio-wildcard')();

io.use(middleware);

io.on('connection', function(socket) {
  socket.on('*', function(){ /* … */ });
});

io.listen(8000);
回调是否可能不只触发disconnect
2021-05-14 11:07:18

干得好 ...

var socket = io.connect();
var globalEvent = "*";
socket.$emit = function (name) {
    if(!this.$events) return false;
    for(var i=0;i<2;++i){
        if(i==0 && name==globalEvent) continue;
        var args = Array.prototype.slice.call(arguments, 1-i);
        var handler = this.$events[i==0?name:globalEvent];
        if(!handler) handler = [];
        if ('function' == typeof handler) handler.apply(this, args);
        else if (io.util.isArray(handler)) {
            var listeners = handler.slice();
            for (var i=0, l=listeners.length; i<l; i++)
                listeners[i].apply(this, args);
        } else return false;
    }
    return true;
};
socket.on(globalEvent,function(event){
    var args = Array.prototype.slice.call(arguments, 1);
    console.log("Global Event = "+event+"; Arguments = "+JSON.stringify(args));
});

这将赶上样事件connectingconnectdisconnectreconnecting太,所以做照顾。

这最终发布了吗?
2021-04-19 11:07:18
Socket.IO.js 版本:0.9.10,开发。
2021-05-04 11:07:18

注意:此答案仅对 socket.io 0.x 有效

您可以覆盖socket.$emit

使用以下代码,您可以使用两个新函数:

  • 捕获所有事件
  • 仅捕获旧方法未捕获的事件(它是默认侦听器)
var original_$emit = socket.$emit;
socket.$emit = function() {
    var args = Array.prototype.slice.call(arguments);
    original_$emit.apply(socket, ['*'].concat(args));
    if(!original_$emit.apply(socket, arguments)) {
        original_$emit.apply(socket, ['default'].concat(args));
    }
}

socket.on('default',function(event, data) {
    console.log('Event not trapped: ' + event + ' - data:' + JSON.stringify(data));
});

socket.on('*',function(event, data) {
    console.log('Event received: ' + event + ' - data:' + JSON.stringify(data));
});
的确。检查@Flion 1.x 版本的答案
2021-04-21 11:07:18
在调用 apply 之前有关 aync 操作的任何建议。setTimeout(function() { original_$emit.apply(socket, ['*'].concat(args)); if(!original_$emit.apply(socket, arguments)) { original_$emit.apply(socket, [ '默认'].concat(args)); } }, 2000);
2021-04-29 11:07:18
我使用Socket.IO 1.3.6和似乎没有要在$ EMIT方法socket
2021-05-02 11:07:18