Nodejs如何把http请求得到的信息及时的用socket.io发送给其他人?

Nodejs如何把http请求得到的信息及时的用socket.io发送给其他人?

app.get(’/info’,function(req,res){
var info = req.body.info;
})

io.sockets.on(‘connection’, function (socket){ socket.broadcast.emit(‘public message’, info); }

需求:A和B是两个NodejsServer,A请求B的/info并提交一个值info,B怎么把这个info的内容通过socket发送给其他所有人?并且A每请求一次socket就广播一次? 我想到的有两种解决方案: 一、把infor先放到一个全局变量里,然后socket去读取,但是这样的话socket得不断监听info值的变化,这样有一些性能浪费,并且可能会不及时,代码如下:

var info = null;
app.get('/info',function(req,res){
    info = req.body.info;
})

io.sockets.on('connection', function (socket){
    setInterval("a();",delaytime);
    function a(){
        socket.broadcast.emit('public message', info);
    }
}

二、A用socket去连接B这样的话就可以把A当作socket的一个客户端了,代码:

io.sockets.on('connection', function (socket){
    socket.on('ServerB',function(msg){
        socket.broadcast.emit('public message', msg);
    });
}

第二种方案不知道有哪些第三方的Server-to-Server的模块可用。

大家有什么好的解决方案,不妨说来听听啊?


3 回复

要实现将HTTP请求得到的信息通过Socket.IO实时发送给其他用户,可以采用一种更高效的方法,即利用中间件或事件机制来处理信息传递。下面是基于您的需求的解决方案。

解决方案

1. 使用中间件传递信息

首先,我们需要确保每次接收到新的HTTP请求时,能够触发一个事件,然后该事件会被监听器捕获并广播给所有连接的客户端。

// 引入必要的模块
const express = require('express');
const http = require('http');
const socketIo = require('socket.io');

// 创建Express应用和HTTP服务器
const app = express();
const server = http.createServer(app);
const io = socketIo(server);

// 存储信息的全局变量
let latestInfo = null;

// HTTP GET路由处理
app.get('/info', (req, res) => {
    const info = req.query.info; // 假设info作为查询参数传递
    latestInfo = info;

    // 触发自定义事件
    io.emit('new info', { info });

    res.send('Info received');
});

// Socket.IO连接处理
io.on('connection', (socket) => {
    console.log('New client connected');

    // 监听自定义事件并广播给所有客户端
    socket.on('new info', (data) => {
        socket.broadcast.emit('public message', data.info);
    });

    // 确保当客户端断开连接时清理资源
    socket.on('disconnect', () => {
        console.log('Client disconnected');
    });
});

// 启动服务器
server.listen(3000, () => {
    console.log('Server is running on port 3000');
});

解释

  1. HTTP请求处理:当客户端向/info发起GET请求时,我们从请求中提取info参数,并将其存储在全局变量latestInfo中。然后,我们使用io.emit方法将新信息广播给所有连接的客户端。

  2. Socket.IO连接处理:每当有新的客户端连接到服务器时,我们将监听名为new info的自定义事件。每当此事件被触发(即有新的信息更新),我们使用socket.broadcast.emit方法将信息广播给所有其他连接的客户端。

这种方法避免了不必要的定时器轮询,从而提高了性能。此外,它确保了信息更新的即时性,因为每次HTTP请求都会立即触发信息的广播。


const redis = require('redis');
const redis_obj = redis.createClient(),
msg_sender = redis.createClient();
redis_obj.on("message", function(t_id, message)
{
    console.log('send one message to ' + t_id );
    socket.emit('message', message);
});

redis有这样的监听数据set的事件,mongodb不知道有木有呢?

根据你的需求,可以采用以下方法将HTTP请求获取的信息通过Socket.IO广播给所有连接的客户端。这里推荐使用第一种方法,但不需要使用setInterval来轮询检查信息变化。当接收到HTTP请求时,直接通过Socket.IO广播消息。

下面是改进后的示例代码:

const express = require('express');
const http = require('http');
const socketIo = require('socket.io');

const app = express();
const server = http.createServer(app);
const io = socketIo(server);

let info = null;

// HTTP 请求处理
app.get('/info', function(req, res) {
    info = req.query.info; // 修改为使用req.query,因为我们传递的是查询参数
    console.log(`Received info: ${info}`);
    
    // 广播信息给所有连接的客户端
    io.sockets.emit('public message', info); 
    res.send({status: 'success'});
});

// Socket.IO 连接处理
io.on('connection', function(socket){
    console.log('A user connected');
    
    socket.on('disconnect', function() {
        console.log('A user disconnected');
    });
});

server.listen(3000, () => {
    console.log('Server is running on port 3000');
});

解释

  1. Express 和 HTTP 服务器设置:创建了一个Express应用实例,并基于该实例创建了一个HTTP服务器。
  2. Socket.IO 设置:使用创建的HTTP服务器初始化Socket.IO实例。
  3. HTTP 请求处理:当接收到/info路径的GET请求时,从请求中提取info参数,更新info变量,并通过Socket.IO广播该信息给所有连接的客户端。
  4. Socket.IO 连接处理:监听客户端连接事件,并在客户端断开连接时打印日志。

这种方法避免了不必要的轮询操作,使得消息传递更加高效和实时。同时,每次HTTP请求都会触发信息广播,满足你的需求。

回到顶部