5. WHAT IS MEMORY ALLOCATION
IN JAVASCRIPT?
Memory allocation = Object creation:
... more ways to create objects
varfoo=[1,2,3];
varfoo={bar:"baz"};
varfoo=newThing();
varfoo=function(){};
varfoo=document.createElement("div");
6. HOW IS MEMORY FREED IN
JAVASCRIPT?
GARBAGE COLLECTION
7. HOW DOES GARBAGE
COLLECTION WORK?
Objects are eligible for Garbage Collection once they
cease to be "alive"
Each object referenced by a "living" object is alive
counted as alive
The garbage collector roots are alive per definition
→ A living object is is part of a retaining tree which starts
at a garbage collection root
9. GARBAGE COLLECTOR ROOTS
What are the garbage collector roots?
Internals of the VM implementation
For our purposes: windowcan be treated like a root
("dominator")
10. MEMORY LEAKS IN
JAVASCRIPT
Memory leaks occur if objects are repeatedly created and
cannot be reclaimed by the garbage collector due to
remaining references.
13. 1. LINKED WEBPAGES, A LITTLE JS
ON EACH PAGE
Navigating between pages resets the VM
Script does not execute over extended periods of time
Leaks have no time to cause trouble
→ NOTHING TO WORRY ABOUT
14. 2. SINGLE PAGE JS APPLICATION
All content generated by JS program
Program runs as long as the page is open
Small leaks accumulate
Browser swallows 100s MB of RAM before crashing!
→ POTENTIAL SHOWSTOPPER!
15. HOW TO AVOID LEAKS?
Simple answer: Always be sure to delete all references to
unused objects.
19. DANGEROUS SPECIAL CASE:
EVENT HANDLERS
functionCounter(elt){
varme=this;
me.count=0;
elt.addEventListener("mousedown",function(){
me.count++;
}
}
varcounter=newCounter(document);
The event handler keeps a reference to the counter
instance
We have no direct reference to the handler
Garbage collection will never happen!
Always leave a way to clean out event handlers (and do
it!), don't throw away those references!
20. DANGEROUS SPECIAL CASE:
DETACHED DOM TREES
vardiv=document.createElement('div');
myFancyElementRegistry.register(div,'somediv');
document.querySelector('.container').appendChild(div);
//...
document.querySelector('.container').innerHTML='';
We keep a reference to the newly created div in a global
registry...
... but remove it from the DOM when clearing its parent
Node remains referenced → detached DOM tree!
Take care to hold no references into DOM trees after they
become detached!
23. MEMORY CONSUMPTION
TIMELINE
For a healthy application, memory consumption should
Rise over time as objects are allocated
Go down when garbage is collected → sawtooth pattern
Baseline after garbage collection should not change
Growing consumption after GC indicates a leak
24. HEAP SNAPSHOTS
Capture a snapshot of the heap contests
Can be filtered by constructor
Living objects can be inspected
Allocated memory size
Differences between snapshots: what leaks?
Retaining trees: why does it leak?
Retaining tree allows to track down the references that
have to be cleaned out!
25. SOME HINTS FOR READING THE
RETAINING TREE
The shortest path is usually most interesting
Inspect what you can — know your enemy
Follow the black objects; gray ones are internals
'context' indicates a function scope
'native' on a DOM node indicates an event handler
Take your time!
26. HEAP ALLOCATION TIMELINE
Shows allocation events
Allocations which have been freed turn light blue
Heap can be inspected filtered based on the time of
allocation
Allows to correlate heap state with events → identify the
code paths that leak
29. DEALING WITH LEAKY LIBRARIES
Common situation:
varsnark=newlibrary.Snark();
snark.on('bark',someObject.handler,someObject);
//...
snark.destroy();
Assuming that the library is buggy, it could retain a
reference to someObject, leading to a leak.
31. GENERAL ADVICE
Profile memory usage early and often
Be extra careful with closures
Unbind event listeners
Be careful with registries
Consider object pooling