node.js应用程序突然加载100%的CPU并挂起

时间:2013-05-22 21:12:19

标签: node.js socket.io

我在linux虚拟机上运行的node.js上有简单的应用程序。它侦听tcp消息并使用socket.io库将它们发送到客户端。经过一段时间的低CPU使用后,突然开始加载CPU越来越高,直到应用程序挂起。脚本很简单,我无法理解它有什么问题。

var net = require('net');
var io = require('socket.io').listen(socketPort);

net.createServer(function (socket) {
    socket.setEncoding("utf8");
    socket.on('data', function (dataStr) {
        console.log("TCP dataStr " + dataStr);
        var data = JSON.parse(dataStr);
        io.sockets.in(data.room).emit('publish', data);
    });
}).listen(tcpPort);

io.sockets.on('connection', function (socket) {

    socket.on('subscribe', function (room) {
        console.log('subscribe room ' + room);
        if (Array.isArray(room)) {
            var i;
            for (i = 0; i < room.length; i++) {
                console.log('subscribe join room ' + room[i]);
                socket.join(room[i]);
            }
        } else if (typeof room === 'string') {
            console.log('subscribe join room ' + room);
            socket.join(room);
        }
    });

    socket.on('unsubscribe', function (room) {
        console.log('unsubscribe room ' + room);

        if (Array.isArray(room)) {
            var i;
            for (i = 0; i < room.length; i++) {
                console.log('unsubscribe leave room ' + room[i]);
                socket.leave(room[i]);
            }
        } else if (typeof room === 'string') {
            console.log('unsubscribe leave room ' + room);
            socket.leave(room);
        }

    });

});

对于集群模块,我尝试运行多个与客户端通信的工作程序。经过一段时间后,每个工作人员都会将自己的CPU核心以100%的速度挂起,并且差不多有一分钟的时间差。

UPD:客户端代码(在浏览器中运行):

    socketObj = new function() {
        var that = this;
        that.socket;

        that.init = function(nodeServerUrl, rooms, onPublishFunc) {
            that.socket = io.connect(nodeServerUrl);
            that.socket.emit('subscribe', rooms);

            that.socket.on('publish', function(data) {
                        onPublishFunc(data);
            });
        };
        that.subscribe = function(room) {
            that.socket.emit('subscribe', room);
        };
        that.unsubscribe = function(room) {
            that.socket.emit('unsubscribe', room);
        };
    }

    ...

    try {
        socketObj.init('application url', ["room1", "room2"], nodeJsCallback);
    } catch(err) {
    }

    ...

    nodeJsCallback = function(jsonData) {
        //Only updates data on UI, no subscribing, unsubscribing, emitting etc.
        ...
    }

UPD2:我试图在生产机器和本地Windows机器上使用合成测试重现问题。我做了一些压力测试:

  1. 多个客户端套接字连接
  2. 多个静态数据下载(浏览器的socket.io脚本)
  3. 增加了tcp更新的频率。
  4. 经过几个小时的测试后,我无法重现。但是当它与真实用户一起运行时,它会在早期或晚些时候挂起。

    我开始认为这是环境或特定的消息问题。可能接下来我会尝试的是:

    1. 将Node.js更新为当前版本
    2. 尝试记录所有数据传输并稍后重播,希望悬挂将重现

1 个答案:

答案 0 :(得分:5)

将Nodejs从版本v0.10.4(稳定)更改为v0.11.2(不稳定)。到目前为止所有的工作都很好,占用了1-2%的CPU。现在我们正在测试v0.10.8(稳定)。

UPD 在v0.10.8上,应用程序也是稳定的。

即使问题在v0.10.4(稳定版)上消失了,但它仍然非常奇怪且令人沮丧。