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.

Possible memory leak – Window object retains after window.close()

See original GitHub issue

This was initally referenced here: https://github.com/tmpvar/jsdom/issues/1493#issuecomment-268248826, but I’d like to create separate topic for that (feel free to close it if necessary).

I wanted to share my findings on using window.close() created with jsdom.jsdom().defaultView. I’ve setup a basic repro with the issue: https://github.com/thymikee/jsdom-leak-repro. Hope it helps someone familiar with jsdom internals to see what’s going on.

Below code is sufficient to retain the Window object:

const jsdom = require('jsdom');
const toMB = bytes => Math.floor(bytes / 1024 / 1024);

function spawnWindow(index) {
  let document = jsdom.jsdom({ url: 'about:blank' });
  let window = document.defaultView;
  const bytes = process.memoryUsage().heapUsed;

  console.log(index, `(${toMB(bytes)} MB)`);

  window.close();
  global.gc(); // force GC to isolate the leak
}

for (let i = 0; i < 200; i++) {
  spawnWindow(i);
}

This is actual problem that we sometimes experience at Jest, here’s on of the relevant issues: https://github.com/facebook/jest/issues/1893

Issue Analytics

  • State:open
  • Created 7 years ago
  • Reactions:4
  • Comments:8 (4 by maintainers)

github_iconTop GitHub Comments

5reactions
thymikeecommented, Feb 1, 2017

@domenic just to give you an update:

  • @romansemko’s example is closer to what happens in Jest, as we dispose environment (i.e. call window.close()) asynchronously
  • we don’t experience this problem on current master (it must have been something internal, but don’t know what 🤷‍♂️)
  • I see 2 easy possibilities on resolving this issue (if you’re able to confirm it):
    1. write about this behaviour in docs (closing window directly after jsdom.jsdom())
    2. change window.close to run asynchronously in the next tick
2reactions
romansemkocommented, Jan 4, 2017

The leakage only happens if jsdom.jsdom and window.close() are synchronous. If I modify your example to fire windows.close() and global.gc() asynchronously, you will see a spike in memory, which will actually drop back to normal after the gc is done. Here the modified example:

https://github.com/romansemko/jsdom-leak-repro

const jsdom = require('jsdom');
const toMB = bytes => Math.floor(bytes / 1024 / 1024);

function spawnWindow(index) {
  let document = jsdom.jsdom({ url: 'about:blank' });
  let window = document.defaultView;

  setTimeout(() => {
    try {
      const bytes = process.memoryUsage().heapUsed;
      console.log(index, `(${toMB(bytes)} MB)`);
    } catch(error) {
      console.log(index);
    }

    window.close();

    if (global.gc) {
      global.gc();
    }
  }, 0)
}

for (let i = 0; i < 200; i++) {
  spawnWindow(i);
}

There is no issue when using jsdom.env istead of jsdom.jsdom, for example, since the code is already fired asynchronously:

function spawnWindow (index) {
    jsdom.env('<html><body>Hi</body></html>', function (err, window) {
        const bytes = process.memoryUsage().heapUsed
        console.log(index, `(${toMB(bytes)} MB)`)
        window.close()
        global.gc()
    });
}

I hope this helps to find the culprit!

Read more comments on GitHub >

github_iconTop Results From Across the Web

Detached window memory leaks - web.dev
The two most common cases where detached windows cause memory leaks are when the parent document retains references to a closed popup or...
Read more >
Causes of Memory Leaks in JavaScript and How to Avoid Them
In this article, we will explore programming patterns that cause memory leaks in JavaScript and explain how to improve memory management.
Read more >
4 Types of Memory Leaks in JavaScript and How to Get Rid Of ...
Learn about memory leaks in JavaScript and what can be done to solve it! ... In JavaScript, the "window" object is an example...
Read more >
WPF Memory leak on window closing - Stack Overflow
For WPF application, there are numerous causes on memory leak. Can be that the event handler hasn't been removed on closing, ...
Read more >
Eradicating Memory Leaks In Javascript - LambdaTest
The setTimeout() and setInterval() are both methods of the HTML DOM Window object. Javascript timers are the most frequent cause of memory leaks ......
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