10

I'm creating a web app to read my e-mails using gmail api. All methods is working (users.messages.list, users.messages.get, etc...) and displaying in console.log and in my page HTML. One thing I have noticed that I have to use atob to decode the body.data and insert in my HTML. Now I have to download or read the attachment for exemple file.docx, and I'm using this exemple here after the callback I noticed that I have to decode too, but if I do, there is no link to download or read, only some code from microsoft word. If I copy this code and create a doc and paste it, says the file is corrupted.

My code:

function getAttachments(messageID, parts, callback) {
    //console.log(parts);
    var attachId = parts.body.attachmentId;
    var request = gapi.client.gmail.users.messages.attachments.get({
        'id': attachId,
        'messageId': messageID,
        'userId': 'me'
    });
    request.execute(function (attachment) {
        callback(parts.filename, parts.mimeType, attachment);
    });
}

if (att.length > 0) {
    for (var i in att) {
        getAttachments(response.id, att[i], function (filename, mimeType, attachment) {
            console.clear();
            console.log(filename, mimeType, attachment);
            console.log(atob(attachment.data.replace(/-/g, '+').replace(/_/g, '/')));
            inline.append('<a href="" style="display: block">' + filename + '</a>');
        });
    }
}

UPDATE

I found a solution here

4
  • How about window.location = 'data:'+mimeType+';base64,'+attachment.data.replace(/-/g, '+').replace(/_/g, '/'); Commented Nov 19, 2015 at 19:39
  • It's worked, but when I click on my link the browser start a download named "download.doc" there is a way to download the doc with the real name? And I realized when I try to download a big file like a .rar (11MB) it doesn't work. Commented Nov 23, 2015 at 13:25
  • The code is: var link = 'data:' + mimeType + ';base64,' + attachment.data.replace(/-/g, '+').replace(/_/g, '/'); inline.append('<a href="' + link + '" style="display: block">' + filename + '</a>'); Commented Nov 23, 2015 at 14:13
  • when i am using gapi.client.gmail.users.messages.attachments.get then it throughs gmail is undefined...and how to pass the authroziation..Plz Commented Nov 16, 2017 at 11:12

1 Answer 1

7

Try this solution.

HTML

<a id="download-attach" download="filename"/>

JS

function getAttachments(messageID, parts, callback) {
    var attachId = parts.body.attachmentId;
    var request = gapi.client.gmail.users.messages.attachments.get({
      'id': attachId,
      'messageId': messageID,
      'userId': 'me'
    });
    request.execute(function (attachment) {
      callback(parts.filename, parts.mimeType, attachment);
    });
  }

if (att.length > 0) {
    for (var i in att) {
       getAttachments(response.id, att[i], function (filename, mimeType, attachment) {

       let dataBase64Rep = attachment.data.replace(/-/g, '+').replace(/_/g, '/')

       let urlBlob = b64toBlob(dataBase64Rep, mimeType, attachment.size)

       let dlnk = document.getElementById('download-attach')
       dlnk.href = urlBlob
       dlnk.download = filename
       dlnk.click()
       URL.revokeObjectURL(urlBlob)
   }
}

function b64toBlob (b64Data, contentType, sliceSize) {
  contentType = contentType || ''
  sliceSize = sliceSize || 512

  var byteCharacters = atob(b64Data)
  var byteArrays = []

  for (var offset = 0; offset < byteCharacters.length; offset += sliceSize) {
    var slice = byteCharacters.slice(offset, offset + sliceSize)

    var byteNumbers = new Array(slice.length)
    for (var i = 0; i < slice.length; i++) {
      byteNumbers[i] = slice.charCodeAt(i)
    }

    var byteArray = new Uint8Array(byteNumbers)

    byteArrays.push(byteArray)
  }

  var blob = new Blob(byteArrays, {type: contentType})
  let urlBlob = URL.createObjectURL(blob)
  return urlBlob
}
Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.