Substituindo socket.io's emit e on?
Pergunta
Durante o desenvolvimento, é muito útil poder ver quais pacotes chegam e são enviados.Isso é possível no lado do servidor com o logger.No lado do cliente, entretanto, não há logger.Encontro-me espalhando console.log por todo o lugar.
É possível substituir socket.emit e socket.on com console.log (argumentos)?Se eu pudesse substituir isso antes do meu soquete, seria muito elegante.
Alguém me aconselhou a substituir o Parser.
Quais são os seus 2 centavos nisso?
Tentei a sugestão de Kato e escrevi o seguinte:
var _origEmit = socket.emit;
socket.emit = function() {
console.log("SENT", Array.prototype.slice.call(arguments));
_origEmit.call(socket, arguments);
};
Isso funciona.No entanto, nem tanto com socket.on.Minha estratégia é envolver cada retorno de chamada com um console.log.Se você conhece python, é como colocar decoradores de função nos callbacks que console.log os argumentos.
(function(socket) {
var _origOn = socket.on;
socket.on = function() {
var args = Array.prototype.slice.call(arguments)
, handlerType = args[0]
, originalCallback = args[1];
var wrappedCallback = function() {
// replace original callback with a function
// wrapped around by console.log
console.log("RECEIVED", Array.prototype.slice.call(arguments));
originalCallback.call(socket, arguments);
}
_origOn.call(socket, [handlerType, wrappedCallback]);
}
Qualquer um pode apontar porque o monkey patching socket.on não está funcionando?
Solução
Para sobrescrever socket.on você realmente precisa sobrescrever socket. $ emit .
O exemplo a seguir funciona tanto no lado do cliente quanto no lado do servidor (testado em socket.io 0.9.0):
(function() {
var emit = socket.emit;
socket.emit = function() {
console.log('***','emit', Array.prototype.slice.call(arguments));
emit.apply(socket, arguments);
};
var $emit = socket.$emit;
socket.$emit = function() {
console.log('***','on',Array.prototype.slice.call(arguments));
$emit.apply(socket, arguments);
};
})();
Outras dicas
Funciona, testado:
var _emit = socket.emit;
_onevent = socket.onevent;
socket.emit = function () { //Override outgoing
//Do your logic here
console.log('***', 'emit', arguments);
_emit.apply(socket, arguments);
};
socket.onevent = function (packet) { //Override incoming
var args = packet.data || [];
//Do your logic here
console.log('***', 'onevent', packet);
_onevent.call(socket, packet);
};
Existe um módulo chamado socket.io-wildcard que permite o uso de curingas no cliente e no servidorlado, não há necessidade de sobrescrever mais nada
var io = require('socket.io')();
var middleware = require('socketio-wildcard')();
io.use(middleware);
io.on('connection', function(socket) {
socket.on('*', function(){ /* … */ });
});
io.listen(8000);
<script src="/socket.io/socket.io.js"></script>
<script>
(function() {
var _origEmit = socket.emit;
socket.emit = function() {
console.log(arguments);
_origEmit.apply(null, Array.prototype.slice.call(arguments));
};
})();
</script>