如何监控来自 express & socket.io 服务器的传入和传出网络字节

How to monitor incoming and outgoing network bytes from express & socket.io servers

我有一个快速服务器,其中还包含 socket.io。我想知道每个客户端的请求(包括 HTTP 和套接字(WSS))有多少字节从外部进入和进入内部。我正在寻找开源技术的解决方案。

我在网上找到了很多教程来获取createServer方法中读取的字节,但是这里我没有使用这种方法,因为我使用了express.js。请参考我下面的代码并帮助我。

我们使用 Nginx 作为生产服务器。

const express = require('express')
const app = express()
const http = require('http').Server(app)
const io = require('socket.io')(http)

app.get('/', (req, res) => {
    res.render('index')
})

http.listen(8080, () => console.log(`Server is running at 0.0.0.0:8080`))

如果你也想捕获 socket.io 统计数据,你需要进入 tcp 层。 node js 中的 tcp 套接字具有这些方便的属性:bytesRead & bytesWritten: https://nodejs.org/dist/latest-v12.x/docs/api/net.html#net_socket_bytesread

当客户端关闭套接字时,使用这些来计算传输的总量。

const http = require('http');
const express = require('express');

const app = express();
const stats = new Map();

setInterval(() => {
    console.log("stats", stats);
}, 3000)

const web = http.createServer(app);

web.on("connection", (socket) => {
    console.log("new connection")

    if (!stats[socket.remoteAddress]) {
        stats[socket.remoteAddress] = {
            receive: 0,
            transmit: 0
        };
    }

    socket.on("close", () => {
        console.log("Save stats")
        stats[socket.remoteAddress].receive += socket.bytesRead;
        stats[socket.remoteAddress].transmit += socket.bytesWritten;
    });
});

web.listen(8080, "127.0.0.1", () => {
    console.log("Running")
});

const io = require("socket.io")(web);

io.on('connection', socket => {
    socket.on("timestamp", (data) => {
        console.log(data)
    });
});

app.get('/', (req, res) => {

    let html = '<script src="/socket.io/socket.io.js"></script>';
    html += '<script>';
    html += '   const socket = io("http://127.0.0.1:8080");';
    html += '   setInterval(() => {socket.emit("timestamp", Date.now())}, 1000)';
    html += '</script>';

    res.end(html);
});

请注意,这衡量了一切,包括。 http header & 其他开销。 不知道socket没有正常关闭会发生什么(超时等)

这不是“失败保存”,您需要添加错误处理和超时内容,这样您就不会错过任何传输的字节。

如果您需要更改任何内容或无法按预期工作,请告诉我!


根据评论/“聊天”更新了答案

const http = require('http');
const express = require('express');

const app = express();
const stats = new Map();

setInterval(() => {
    console.log("stats", stats);
}, 3000)



const web = http.createServer(app);


web.listen(8080, "127.0.0.1", () => {
    console.log("Running")
});


const io = require("socket.io")(web);



app.get('/', (req, res) => {

    const { socket } = req;

    if (!stats[socket.remoteAddress]) {
        stats[socket.remoteAddress] = {
            receive: 0,
            transmit: 0
        };
    }

    socket.once("close", () => {
        console.log("Save stats")
        stats[socket.remoteAddress].receive += socket.bytesRead;
        stats[socket.remoteAddress].transmit += socket.bytesWritten;
    });

    res.end("Hello World");

});

这只计算路由上的 http 请求 /,没有 websockets 只是普通的 http。