2015-06-10 11 views
6

Ich schrieb Code unter Verwendung von Nodejs und socket.io für eine einfache Socket-Anwendung (nur verbinden und trennen), für etwa 50 Benutzer Speicherverbrauch nicht zu viel ändern, aber für bis zu 300 Benutzer und nach einer Stunde, Speicherverbrauch nur wachsen (in der Nähe von 300 MB für server.js Prozess und wächst nach Zeit verstreichen), es sieht aus wie diese Nodejs nicht Speicher freigeben.nodejs, socket.io einfacher Code Speicherleck

var server = require('http').createServer(); 
var io = require('socket.io')(server); 
var port = 9090; 
var sockets = {}; 

server.listen(port, function() { 
    console.log('Server listening at port ', port); 
    //timer and logs are not problem , i tested it before. 
    setInterval(function(){ 
     console.log(Object.keys(sockets).length+' Online Devices At '+Date()); 
    }, 1000 * 60 * 1); 
}); 

io.on('connection',function(socket){ 
    sockets[socket.id]={id:socket.id}; 
    console.log('connected '+socket.id + ' count ' + Object.keys(sockets).length); 
    socket.on('disconnect', function (data) { 
     delete sockets[socket.id]; 
     console.log('disconnected '+socket.id+ ' count ' +Object.keys(sockets).length); 
    }); 
}); 

mache ich etwas falsch ?!

bearbeiten

14 Stunden nach forever enter image description here

300 offenen Steckdosen mit Datei starten und über 500 MB Speichernutzung, die zu meinem NodeJS proccess verwendet ist.

bearbeiten

Nach 16 Stunden, 300 Connected Sockets enter image description here Nach Prozess gestoppt. enter image description here

bearbeiten

Beute an meinem neuen Code Bitte übertragen.

var server = require('http').createServer(); 
var io = require('socket.io')(server); 
var port = 90; 
var counter = 0; 
var clients = {} 
server.listen(port, function() { 
     console.log('Server listening at port ', port); 
}); 
io.on("connection",function(socket){ 
     clients[socket.id] = socket; 
     counter++; 

     socket.on('disconnect', function (data) { 
       counter--; 
       delete clients[socket.id]; 
     }); 
}); 

Ich versuche, dies mit 1000 angeschlossenen Benutzern (ein anderer Server ist Simulieren Benutzeranforderungen und offene Steckdosen)

Speichernutzung vor dem Start: 100MB, nach 5 Minuten und 1000 stabil offenen Verbindungen: 400MB

Antwort

0

Der Code sieht gut aus. Ihr vorgeschlagener Speicherverlust ist fast sicher nicht in dem Teil des Codes, den Sie freigegeben haben.

Dies ist zu Ihrer Hauptfrage nicht relevant, aber wenn Sie nur die Anzahl der angeschlossenen Steckdosen zur Liste möchten, sollten Sie einen Integer-Zähler anstelle Object.keys() der Aufruf auf dem sockets Objekt, wie folgt aus:

var express = require('express'); 
var app  = express(); 
var server = require('http').createServer(app); 
var io  = require('socket.io')(server); 

var port = 9090; 
var connectedSockets = 0; 
var sockets = {}; 

server.listen(port, function() { 
    console.log('Server listening at port ', port); 
    //timer and logs are not problem , i tested it before. 
    setInterval(function(){ 
     console.log(connectedSockets + ' Online Devices At ' + Date()); 
    }, 1000 * 60 * 1); 
}); 

io.on('connection',function(socket){ 
    if (!sockets[socket.id]) connectedSockets++; 
    sockets[socket.id]={ id: socket.id }; 
    console.log('connected ' + socket.id + ' count ' + connectedSockets); 
    socket.on('disconnect', function (data) { 
     delete sockets[socket.id]; 
     connectedSockets--; 
     console.log('disconnected ' + socket.id + ' count ' + connectedSockets); 
    }); 
}); 
+0

Was manuell einen Zähler beibehalten, wenn das Sockets-Objekt bereits eine Liste der verbundenen Sockets hat? Was hat das mit der gestellten Frage zu tun? – jfriend00

+0

@galactocalypse, zuerst danke für deine Antwort aber 'Dein vorgeschlagener Speicherverlust ist fast sicher nicht in dem Teil des Codes, den du geteilt hast. Das sind alle meine Codes! . 'über das Zählen von Steckdosen 'weiß ich das! , aber ich habe versucht, zu zeigen, dass dieses Problem NICHT das Unscharfschalten von Variablen oder Array-Elementen betrifft. – Mojtabye

+0

@ jfriend00: Ich hatte am Anfang dieses Punktes erwähnt, dass es "Dies ist nicht relevant für Ihre Hauptfrage". Object.keys() läuft in O (n) und während 300 nicht viel ist, wird O (1) sicherlich in einem signifikant höheren Maßstab vorzuziehen sein. @ ALU0075: Ich schlage vor, Sie nehmen einen Heapdump und teilen, was Sie finden, wie hier vorgeschlagen: 'http://jpallen.net/2013/03/08/tracking-down-a-memory-leak-in-node-js -und-socket-io/'Teilen Sie auch die von Ihnen verwendeten node- und socketio-Versionen. – galactocalypse

9

V8 ist faul, wenn es darum geht, ungenutzten Speicher freizugeben, so dass es wie ein Speicherleck aussieht, wenn V8 gerade nicht seinen Garbage Collector ausführt. Um zu sehen, ob dies der Fall ist, führen Sie Ihren Prozess mit dem --expose-gc Flag aus, das z.

node --expose-gc yourscript.js 

Und erzwingen manuelle Garbage Collection in einem Intervall (Ich habe 30 Sekunden Intervall).

setInterval(function(){ 
    global.gc(); 
    console.log('GC done') 
}, 1000*30); 
+0

danke, aber überprüfe meinen neuen Code! , auch nach dem Trennen von 1000 Sockets und mit Array-Größe 0 und ohne Protokoll, 300MB für 5 Minuten ist zu viel: | – Mojtabye

+0

Was passiert, wenn Sie das Objekt "Clients" vollständig aus dem Code entfernen? Findest du immer noch das Leck? –

+1

selben ERGEBNIS! Ich habe das Gefühl, dass da etwas nicht stimmt mit socket.io – Mojtabye