I wrote a java script web page, and i want to detect automatically parts of codes that cause a memory leak in that page( for example creating timer objects and not releasing them).
i want to do it automatically because when i leave the browser open (with this page) it crashes only after two days.
I am familiar with the Chrome dev tool that allows taking snapshots and comparing them.
However, it requires taking snapshots and making the comparison manually.
I was wondering, is it possible to programmatically detect memory leaks without the need for a manual intervention?
Related
I am using Chrome v73. I have a memory leak in my web application. I can see all mentioned parameters increasing drastically. I want to know what it is and which one I can refer to and fix accordingly.
I suspect my one-page javascript app contains a memory leak somewhere. Weak devices running Firefox or Chrome seem to crash eventually if the page is left open. I'm trying to determine whether reloading the page would be expected to free the memory or not.
I understand that memory handling is specific to the browser, so the answer may differ in Chrome or Firefox.
NOTE: I recognize that browsers are mentioned a lot in this question (which would be off topic), but the point of this question is about javascript debugging, which I think is very on topic.
Barring browser/extension bug, browsers free up resources when they are no longer needed; Firefox clears compartments, Chrome kills processes and associated storage.
Firefox does its best but may take some time to clear the memory and may create zombie compartments on occasion:
Compartments are destroyed when they are garbage collected. This happens some time after the last reference to them disappears. This means there can be a delay between a page being closed and its compartments disappearing...
Sometimes, due to bugs in Firefox, the Add-on SDK and/or add-ons, compartments are created that are never destroyed. These are a particular kind of memory leak, and they cause Firefox's memory usage to increase gradually over time, slowing it down and making it more likely to crash.
Chrome uses a process per tab (and really subprocesses for some entities within a tab as well IIRC e.g. plugins, iframes, etc.) to the same effect. Though a quick check against chrome://memory-redirect/ and refreshing a tab looks like the same pid is used. So a refresh is not a completely clean slate.
FWIW Chrome has a "Force Reload" that clears the cache and might be either useful for clearing more memory or a placebo: cmd-shift-r
I'm not really familiar with the internals but I've only seen things not reliably freed up between refreshes when a particular browser is getting too clever and trying to preserve things when you're not changing origins etc. in an effort to boost load performance.
In short, you could be tripping up a browser bug if you're not seeing memory freed as you expect but you'd want to use the various "about:memory" tools to verify that and at that point it would be on you to avoid such behavior and/or report the issue to the browser's dev team.
Otherwise, I think you're best served by addressing your own memory leaks within the page using the various tools available.
A good way to debug the resource usage of JS is to use the Firefox performance monitor within the inspection tool. Firefox Dev Edition has more in-depth tools
Press F12 when on the page and click on the little speedometer icon in the inspect window; this will open the performance monitor. Press the "Start Recording" button and Firefox will begin to benchmark all script timings, CSS activity, user input etc. on the page.
When you feel that it has been running for long enough, stop recording and you will be presented with all the data. At the top will be a chart displaying performance and you can click on any part and examine all the scripts running at that time.
A full tutorial for the performance tools can be found here
I just finished writing tests for JavaScript application and I was using Jasmine for the first time. Everything works fine, but I still need to test if application has some memory leaks within. Is it even possible to programmatically check it within my specs? Maybe there is some additional library for this?
Chrome has a non-standard extension of the window.performance API -- (window.performance.memory), where you can measure memory usage.
In order to enable precise memory statistics, you must use this flag: --enable-precise-memory-info
But you also need to force GC to tell whether memory is retained after your test. Because CG doesn't happen instantly.
With Chromium browser, you can run it with a special command flag to expose a method to force GC:
chromium-browser --js-flags='--expose_gc'
This gets you access to the method window.gc().
As I know there is no automatic way to find source of javascript memory leak. Javascript memory leaks is realy nasty thing on which you can waste a lot of time. Recently I was developing very large enterprise web solution as a single page application with almost 1mb of minimized self-written code. Suddenly we realized that our application is leaking hard. I tryied hundreds of technics to find the source of memory leak and the easiest way for me is to use google chrome profiler, take heap snapshot and compare different heap snapshots. Here is more information how to do it :
https://developer.chrome.com/devtools/docs/javascript-memory-profiling
Have a nice week with debugging memory leaks in your app, hope it will take less time that in my case. :)
We have developed a Samsung Smart TV app for the 2011 & 2012 platforms. The app is HTML/JavaScript based. Normally the app is performing well, but after exiting the app becomes very slow, by a factor of six. The measured JS execution times are only slightly slower, but the HTML elements are rendered much slower to the screen. This behavior happens on all devices (TV and Blu-Ray Player devices with Smart TV Platform).
The exit is realized by executing the JS command
var widgetAPI = new Common.API.Widget();
widgetAPI.sendExitEvent();
The app behaves the same (i.e. becomes slower after starting again) when using the command
widgetAPI.sendReturnEvent();
(which returns the user to the Smart Hub instead of exiting completely). Through trial and error I discovered that making the app crash on purpose solves the problem - this results in an identical behaviour to the user as calling the sendExitEvent method. However, it is not a very clean method, and furthermore I would prefer to use the sendReturnEvent command.
How can I return the user to the Smart Hub programatically so that the app does not get slower when starting it again?
I hope somebody has some first-person experience and advice regarding this. I have tried to eliminate possible JS memory leak sources (using JS programming best practices and advice from Samsung), but that has not remedied the problem.
I solved the problem using two actions:
Instead of simply calling widgetAPI.sendReturnEvent() I redirect the user to a new page exit.html (using window.location.href), which is almost empty, except for an onload handler, which calls the following commands (which are equivalent to widgetApi.sendReadyEvent() and widgetApi.sendReturnEvent() but without needing to include the Widget.js file)
curWidget.setPreference("ready","true");
curWidget.setPreference("return","true");
Commenting out all alert commands. Apparently calling alert leaks memory when used several times so that the accumulated garbage is not collected from the memory when exiting the app, causing it to be slower after restart
Only applying the both methods seemed to fix the issue. Presumably the app accumulates memory leaks causing the app being slow after restart
1) on the document level (despite our efforts to follow all guidelines to prevent them), which are then purged after loading another HTML file.
2) on a global level, caused by calling alert
This question already has answers here:
Closed 10 years ago.
Possible Duplicate:
What is the best way to profile javascript execution?
I have a few scripts that use jQuery, and I think I have a memory leak in one of them.
How one could profile and find what parts of the scripts that I have are using the most memory/CPU?
Regarding memory consumption
Memory leaks in JavaScript are usually ignored except when they turn into browser memory leaks (that is, even after the user navigates away from the page, the memory continues allocated and there's no way to free it). The reason for this is that while your web application may have some memory leaks, users will go from one page into another so the leaks are minimized. However they may not restart the browser, so browser memory leaks may be serious. Some JavaScript code is known to cause memory leaks on certain browsers, being Internet Explorer probably the worst in this area. For it you may find Microsoft JavaScript Memory Leak Detector to be very useful.
Regarding times
IE, Chrome and Safari have built in profilers in the web development tools that ship with the browser. For Firefox you may use Firebug. Also useful may be, since you're using jQuery which means your profiling report will be filled with anonymous functions and alike, making it quite unreadable, John Resig's jQuery profiling plugin, which will give you a clearer output on the matter.
Use Firebug. To quote from http://getfirebug.com/js.html:
To use the profiler, just go to the Console tab and click the "Profile" button. Then use your app for a bit or reload the page and then click the "Profile" button again. You'll then see a detailed report that shows what functions were called and how much time each one took.
I would suggest taking a look at the profiler in Firebug, and the Drip plugin for IE to help look for memory leaks.
Also, just keep in mind that most javascript memory leaks come from circular references between DOM objects and javascript objects not being broken when the DOM object is unloaded. To prevent that, I would suggest avoiding creating references to javascript objects in DOM object properties (ie, avoid something like document.getElementById('foo').bar = myObject;). If you must create these circular references, be sure to break them yourself in a function that runs when the page unloads, or when removing the DOM objects prior to unload.
Google Chrome also has profile options
Another simple way to test a specific piece of code is to add a timer around it.
var testStart = new Date();
// code to be tested here
$('#jstest').html("selected function: "+ (new Date() - testStart) + " milliseconds");
Where jstest is a span element somewhere visible on your page.
Though chrome has profiling options inbuilt it does not give precise information about the object.So i prefer using leak-finder-for-javascript tool which helped me in my code.
https://code.google.com/p/leak-finder-for-javascript/
I hope this helps.
Firebug or Google's Page Speed for Firefox have profiling tools.
This post by John Resig (jQuery) may be helpful for detecting memory leaks in IE:
http://ejohn.org/blog/deep-tracing-of-internet-explorer/