Me and my team facing one issue of memory in our application. The issue is whenever we trigger jsPDF instance its works but after that it's holding lot of memory and we facing performance issue because its never release that memory after completion of task. For reference i prepare one example and you can check with that. https://stackblitz.com/edit/web-platform-vkewvw?file=index.html
So in this example you see my memory footprint its some around 36 MB you can see on first screen shotenter image description here
and after run the code its goes around 56MB and its not releasing the memory you see in the next screen shot. enter image description here
Can any one help on that how we overcome that problem we tried with iframe itself by not working properly.
Your help is appreciable for us.
As raised in comment, altering the timing of revoking blob urls may improve memory handling in an application using JSPDF
, but does not come with a guarantee to do so ...
The Blob Store
User agents maintain a blob ULR store that keeps a reference to Blob objects keyed by the urls for them returned from URL.createObjectURL(blob)
. Holding a reference in the store stops the blob object from being garbage collected from memory even if JavaScript code has not kept a reference to the blob object itself.
The blob object can be removed from the URL store by calling URL.revokeObjectURL(blobURL)
, after which the blob is eligible for garbage collection from memory provided no reference to it is reachable in JS.
Now jsPDF
sets its global object to window
in browsers' main JavaScript thread in globalObject.js, and imports the global object as _global
in FileSaver.js
.
Lines 85 and 86 of FileSaver.js
define the module's saveAs
export as
var saveAs =
_global.saveAs ||
... code for saving file
which implies you should be able to shim the saveAs
function for experimental purposes by declaring a shim (using function saveAs
or window.saveAs =
) in file level script before including jsPDF.js
in the HTML document.
Initially you could use the original saveAs
code with console logs to demonstrate the shimming process works and that jsPDF
still works. Things I would want to look at include
saveAs
to save the PDF file produced?FileSave.js
(linked above), materially affect performance of the application?FileSave.js
?Synchronous Revocation of Blob URLs
There is some possibility that Blob URLs can be revoked synchronously after use. The following code (which doesn't work as a code snippet) creates a blob and downloads it:
function blobURL(string) {
const blob = new Blob(Array.from(string));
return URL.createObjectURL(blob); // see NOTE 1
}
const url = blobURL("hello folks and world");
console.log("2 seconds...");
setTimeout( saveBlob, 2000, url); // see NOTE 2
function saveBlob(url) {
const link = document.createElement('a');
link.setAttribute("download", "hello.txt");
link.href= url;
document.body.appendChild(link);
link.click();
URL.revokeObjectURL(url); // SEE NOTE 3
console.log("Call to link.click() has returned");
}
Note
link.click()
, before returning to the event loop.Calling URL.revokeObjectURL()
immediately after programatially clicking the link to download the blob did not affect the success of downloading in Firefox or Edge/webkit when tested. This implies that these browsers synchronously obtains a reference to the Blob instance (using Blob Store lookup) before returning from link.click()
.
This is consistent with the behavior of events programmatically dispatched on an element being processed synchronously (which I looked at recently in answer to "Do events bubble in microtasks?"). How safe it is to make use of this in production, however, is not something I am personally in a position to guarantee across all browsers.