Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Spawn Download with Client Side Script

In an application that runs client-side, in browser, written in Javascript, you can use local storage to persist state. If the user requires the ability to extract their data from the client-side application, one option is posting the content to the server and having the server echo it back with the correct content-type and other headers to spawn a download operation.

Is there any way to spawn such a download operation using purely client-side script, without posting the content to a server and echoing it back?

like image 770
Xharlie Avatar asked Mar 19 '23 01:03

Xharlie


2 Answers

I have discovered how to do this: you can use Blob, createObjectURL() and anchor tags.

This JSFiddle shows a solution that works in Chrome and Internet Explorer and even supports drag-and-drop saving in Chrome (you can drag the Save-button into Windows Explorer to save the document.) http://jsfiddle.net/fa9y6/9/

First, you must construct a Blob to save:

var blob = new Blob([ $('#documentContent').val() ], { type: mimeType });

Saving it as a file is easiest in Internet Explorer:

if (window.navigator.msSaveOrOpenBlob) {
    window.navigator.msSaveOrOpenBlob(blob, filename); 
}

In Chrome (and Firefox), you can construct an anchor tag and click() it:

var a = document.createElement('a');
a.download = filename;
a.href = window.URL.createObjectURL(blob);
a.click();
if (a.remove) a.remove();

To support drag-and-drop file saving, you need to attach a handler to dragstart:

if (window.chrome) {
     document.body.addEventListener('dragstart', function(e) {
         // Some use a class, here. My sample only has one save button.
         if (e.target.id == 'downloadButton') {      
             var blob = new Blob([ $('#documentContent').val() ], { type: mimeType });
             e.dataTransfer.setData('DownloadURL', [mimeType, $('#fileName').val(), window.URL.createObjectURL(blob)].join(':'));
         }
     });
}

(I have not performed thorough browser-compatibility testing in older browser versions.)

like image 56
Xharlie Avatar answered Mar 21 '23 15:03

Xharlie


Check out FileSaver.js which provides a saveAs function:

var blob = new Blob(["Hello, world!"], {type: "text/plain;charset=utf-8"});
saveAs(blob, "hello world.txt");

It's compatible with IE10+.

like image 32
Tamlyn Avatar answered Mar 21 '23 15:03

Tamlyn