question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

Memory Leak: `material_select` never removes global `click` handlers

See original GitHub issue

Description

$.material_select installs multiple global click handlers on window, but never cleans them up:

https://github.com/Dogfalo/materialize/blob/28af85de90bad5e7347d7882116fdfca098659f2/js/forms.js#L641

This results in a memory leak in single-page applications that call this function when rendering a view. Every time the function is called, new global click handlers are added. Since they are never removed, the browser cannot garbage collect the handler or any data within its closure (which includes DOM NodeLists within jQuery objects).

Is there a way to either avoid a global click handler, to only install a single global click handler, or to clean up global click handlers at some point?

Repro Steps

N/A

Screenshots / Codepen

N/A

Issue Analytics

  • State:closed
  • Created 7 years ago
  • Reactions:3
  • Comments:5

github_iconTop GitHub Comments

1reaction
r3wtcommented, Feb 20, 2017

@jvilk

the lifecycle of SPA’s are beyond the scope of jQuery plugins. one approach you might take is to override jQuery’s init() method and use it to maintain a list of selectors with bound events, and use the well known hack to remove all events.

override $.fn.init:

var watchedSelectors = [];
$.fn.init = function(selector,context)
{
    //you could maybe add some logic to see if you want to watch it or not.
    var jQinstance = new jQselector(selector,context||window.document,$);
    
    watchedSelectors.push(selector);

    return jQinstance;
};

remove events when needed:

for(var i=0;i<watchedSelectors.length;i++){
        $(watchedSelectors[i]).find("*").addBack().off();
}
watchedSelectors.length = 0;

you could probably take it a bit further and remove from specific selectors, but i’ll leave that exercise up to you.

0reactions
fegacommented, Apr 15, 2017

@r3wt thanks! 😄

Read more comments on GitHub >

github_iconTop Results From Across the Web

javascript memory leak when DOM element deleted, what kind ...
The Foo variable to store your instance is global, and Foo.child is still a globally accessible reference. But even you didn't store the ......
Read more >
Are you afraid of event handlers because of C# memory leak ...
The answer is, No, I mean, not always. But, please note. I did not say 'Never.' I said, 'Not always.' That means, yes,...
Read more >
Causes of Memory Leaks in JavaScript and How to Avoid Them
Common Sources of Memory Leaks in JavaScript Code # · 1. Accidental global variables · 2. Closures · 3. Timers · 4. Event...
Read more >
How to fix the React memory leak warning - DEV Community ‍ ‍
Global variables are never garbage collected so don't forget to remove event handlers manually if the event emitter is stored in a global...
Read more >
Righting Web Development - ScholarWorks@UMass Amherst
BLeak is the first system for automatically debugging memory leaks ... [137] Vilk, John. Memory Leak: material select never removes global click handlers....
Read more >

github_iconTop Related Medium Post

No results found

github_iconTop Related StackOverflow Question

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found