I am trying to use ng-grid to visualize high-frequency data in real time, but I am having problems with a memory leak. There is no memory leak when I use a simple html table with ng-repeat.
I use node + express on the backend and angularjs on the client side. I use socket.io to stream in real time from a server to a client-side table.
I reproduced the memory problem in a simplified example:
I send 1500 messages per second, each message is an object like this {id: 1, name: "name", time: "[current date / time string]"} after 4 minutes, the browser memory exceeds 400MiB and after 10 minutes above 1GiB
I tested Chrome and Firefox.
Here is a simplified example, am I doing something wrong? (Additional information is added at the end).
server
var app = express();
var server = require('http').createServer(app);
var io = require('socket.io').listen(server);
io.of('/test').on('connection', function (socket) {
console.log('socket connection: /test');
for (id=1; id<16; id++) {
streamData(id);
}
function streamData(id) {
setInterval(function () {
socket.emit('updateData', {
id: id,
name: "test"+id,
time: (new Date()).toString()
});
}, 10);
}
});
service using angular-socket-io
factory('testSocket', function(socketFactory) {
return socketFactory({
ioSocket: io.connect('http://localhost/test')
});
})
controller
controller('NgGridTestCtrl', function ($scope, testSocket) {
var itemsObj = {};
$scope.items = [];
$scope.gridOptions = {
data: 'items',
columnDefs: [{field:'id', displayName:'ID', width:'15%'},
{field:'name', displayName:'Name', width:'20%'},
{field:'time', displayName:'Date and Time', width:'65%'}],
enableColumnResize: true
};
testSocket.on('updateData', function(data) {
itemsObj[data.id] = data;
var values = [];
angular.forEach(itemsObj, function(value, index) {
this.push(value);
}, values);
$scope.items = values;
});
});
NgGrid Template
<div>
<h1>ng-grid table</h1>
<div class="gridStyle" ng-grid="gridOptions"></div>
</div>
Edited to add a simple table example
Using a simple table does not give memory problems, browser memory remains about 155 MB
controller
controller('SimpleTableCtrl', function ($scope, testSocket) {
$scope.items = {};
testSocket.on('updateData', function(data) {
$scope.items[data.id] = data;
});
}).
simple table template
<div>
<h1>Simple table with ng-repeat</h1>
<table class="table">
<thead>
<tr>
<th>ID</th>
<th>Name</th>
<th>Time</th>
</tr>
</thead>
<tbody>
<tr ng-repeat="item in items">
<td>{{item.id}}</td>
<td>{{item.name}}</td>
<td>{{item.time}}</td>
</tr>
</tbody>
</table>
Additional observations
- The memory problem is not only related to the ng grid; it also manifests itself using the NgGridTestCtrl controller with a "simple table template" with ng-repeat.
- A memory problem does not occur (with the ng-grid and NgGridTestCtrl patterns) if the data frequency is lower (500 milliseconds instead of the 10 millisecond interval in the streamData function).
- - ( NgGridCtrl), (500 10 streamData). , .
- "SimpleTableCtrl" " ".
- ng- . - , ng-grid ?