如何在Socket.io模块化事件中传递socket实例给回调函数
Socket.io事件回调中传递socket实例的解决方案
问题场景
我按如下方式构建Socket.io服务:
const io = require('socket.io')(server, { cors: { origin: "*" } });
// sockets events const onConnection = require('./sockets/events/connection');
io.on("connection", onConnection);
连接事件处理逻辑:
const search = require('./search'); // 注:原代码存在笔误,已修正 const onConnection = async (socket) => { console.log(`Client connected ${socket.id}`); socket.on('search', search); socket.on('disconnect', (reason) => { console.log(`Client disconnected with reason: ${reason}`) }) }; module.exports = onConnection;
search函数代码:
const onSearch = async (socket) => { console.log(socket); console.log(500); } module.exports = onSearch;
我需要在search函数中获取socket实例以调用相关方法,尝试直接调用socket.on('search', search(socket))但无效。
可行解决方案
方案1:箭头函数包裹回调
在绑定事件时,用箭头函数把socket和事件参数一起传递给search函数:
// 在onConnection中修改绑定代码 socket.on('search', (data) => search(socket, data));
同时修改search函数,接收socket和事件数据参数:
const onSearch = async (socket, data) => { console.log('socket实例:', socket); console.log('客户端传来的搜索数据:', data); // 这里可以调用socket.emit等方法 socket.emit('search-result', '返回结果'); } module.exports = onSearch;
方案2:利用this绑定
Socket.io的事件回调中,this默认指向当前socket实例(注意不能用箭头函数作为回调,否则this会丢失)。有两种实现方式:
方式A:直接在search中使用this
修改search函数为普通函数(不要用箭头函数):
const onSearch = async function(data) { console.log('socket实例:', this); console.log('客户端数据:', data); this.emit('search-result', '结果'); } module.exports = onSearch;
绑定事件时直接传函数:
socket.on('search', search);
方式B:显式绑定this
如果search是箭头函数(无法通过this获取),可以用bind绑定socket:
// 在onConnection中 socket.on('search', search.bind(socket));
此时search函数的第一个参数是事件数据:
const onSearch = async (data) => { console.log('socket实例:', this); // 这里this就是绑定的socket console.log('客户端数据:', data); } module.exports = onSearch;
方案3:高阶函数返回回调
把search改成高阶函数,接收socket后返回一个处理事件的函数:
// search.js const onSearch = (socket) => async (data) => { console.log('socket实例:', socket); console.log('客户端数据:', data); socket.emit('search-result', '结果'); } module.exports = onSearch;
然后在onConnection中调用search并传入socket,返回的函数作为事件回调:
// 在onConnection中 socket.on('search', search(socket));
为什么直接调用search(socket)无效?
当你写socket.on('search', search(socket))时,会立即执行search(socket)并把它的返回值(这里是一个Promise)作为回调,但Socket.io需要的是一个函数类型的回调,所以这种方式会导致绑定失败。
内容的提问来源于stack exchange,提问作者KyuolDa
相关产品推荐
相关产品推荐

