Memory leak (context.set / flex.set / global.set)

Hello Everyone!
Not long ago I started using the latest version (3.1.0) of Node-Red with Node v18.18.2, and I noticed that a memory leak appeared on my devices (Raspberry Pi 3+, Orange Pi PC+). After about a week of use, my devices restarts due to lack of memory. Before the update I was using version 3.0.2.
I compared the dumps (after boot vs after 5 days) and saw that most of the memory is occupied by the objects that I save through the functions context.set / flex.set / global.set.

Can someone tell me how to properly use these context.set / flex.set / global.set functions and what is not recommended to do when using them? I read the documentation, but there is no description of what it is not recommended to do.

It's up to you what you put in context. If you fill an array or object and don't free it/delete it, it will stay in memory.

Hard to give any advice as you don't clearly state how you are using context.

For example, are you populating an array? Do you ever clear it out?

It's not array, it's just object with few fields and another objects.
Code example:

// myObj - created in another function:
var myObj = global.get('myObj');
var myObjPrev = context.get('myObjPrev') || myObj;

// compare current and previus obj and to do something...

// deep copy object
context.set( 'myObjPrev', JSON.parse(JSON.stringify(myObj)) )

// Sometimes I use Lodash
context.set( 'myObjPrev', _.cloneDeep(myObj) );

Of course, I understand that if it were an array, I would need to monitor its size, but in my case it is only an object that is overwritten with a new object (cloned) every time it is called.
Do I understand correctly that before calling a function context.set I need to delete the object (myObjPrev = undefined )?

No, you should not need to do that. The memory should automatically be freed when there are no remaining references to the data.
I have just run an intensive test using a 1MB Buffer, cloning it as you do and storing in context. This is repeated 10 times per second and over a significant time I saw no increase in memory usage.

If you run top while node-red is running do you see the memory used by node-red increasing?
When using top, the 'avail Mem' figure tells you the total amount of memory available for re-use.

Yes, I see ('avail Mem') that over the last 3 days the memory has decreased by approximately 150 MB ((

How much memory have you got?

There is 1GB RAM

From what amount?

How much does it say node red is using?

Was free about 620MB, now 439. And now Node-Red use 44.4% of memory

What else do your flows do? Do you have contrib nodes in use? Are you working with database(s)? Are you making HTTP requests & how frequently? How frequent are you writing to context? Do you have loops in your flows?

Lastly, I would recommend you use the built-in util for cloning const clone = RED.util.cloneMessage(myObj)

It is perfectly normal to see Node-RED memory increase over time and then reduce as this is how the garbage collection process works. Node.js only recovers memory when it needs to.

This topic was automatically closed 60 days after the last reply. New replies are no longer allowed.