Filesaver.js: Wrong encoding when downloading binary data

Created on 8 Jun 2016  路  5Comments  路  Source: eligrey/FileSaver.js

Hi!

I have following situation:

I call a servlet in javascript. The servlet returns a byte stream of a PDF file.

$.ajax({
  url: url,
  type: 'GET',
  success: function (data) { 
      var blob = new Blob([data], {type: "application/octet-stream"});
      var fileName = "test.pdf";
      saveAs(blob, fileName);
  },
  error: function(data) {alert('Error: ' + data.value)},
});

The file is downloaded but badly in a wrong encoding!
When i dowload the data in the servlet to a file its different to the file saved via your script. See attachments. How can this be done correctly?

viaFileSaverScript.pdf
fromServlet.pdf

Thanks!

Make a Blob

Most helpful comment

I have forgotten mostly all about jQuery. But you should fetch the data as a blob directly using xhrFields...

url: url,
xhrFields: {
      responseType : 'blob'
}

jquery is trying to download the data as plain text and encode it, you don't want that

All 5 comments

I have forgotten mostly all about jQuery. But you should fetch the data as a blob directly using xhrFields...

url: url,
xhrFields: {
      responseType : 'blob'
}

jquery is trying to download the data as plain text and encode it, you don't want that

Thanks for the fast reply!

Now i get

jquery-2.1.3.min.js?v=5.0.2.00.07:4 Uncaught InvalidStateError: Failed to read the 'responseText' property from 'XMLHttpRequest': The value is only accessible if the object's 'responseType' is '' or 'text' (was 'blob').

Made it now with help of
http://stackoverflow.com/questions/29023509/handling-error-messages-when-retrieving-a-blob-via-ajax

var ajax = new XMLHttpRequest();
ajax.open("GET",url,true);
    ajax.onreadystatechange = function(){
        if(this.readyState == 4) {
            if(this.status == 200) {
                console.log(typeof this.response); // should be a blob
                    var blob = new Blob([this.response], {type: "application/octet-stream"});
                  var fileName = "test.pdf";
                  saveAs(blob, fileName);
            } else if(this.responseText != "") {
                console.log(this.responseText);
            }
        } else if(this.readyState == 2) {
            if(this.status == 200) {
                this.responseType = "blob";
            } else {
                this.responseType = "text";
            }
        }
    };
ajax.send(null);

Good, i was going to say that most stackoverflow answer and articles refer to using plain xhr, as jquery don't have support for responseType yet

However, I found this transport that adds responseType support to jquery's ajax
http://www.henryalgus.com/reading-binary-files-using-jquery-ajax/

Another solution is to use the new ajax api: fetch

fetch(url)
.then(function(res){
  return res.blob()
})
.then(funciton(blob){
  saveAs(blob, 'filename')
})
Was this page helpful?
0 / 5 - 0 ratings

Related issues

mluis picture mluis  路  3Comments

rhyous picture rhyous  路  6Comments

nomego picture nomego  路  6Comments

capaj picture capaj  路  4Comments

meenucoditas picture meenucoditas  路  6Comments