title: Converting byte array output into Blob corrupts file
body: <p>I am using the Office Javascript API to write an Add-in for Word using Angular.</p>
  
  <p>I want to retrieve the Word document through the API, then convert it to a file and upload it via POST to a server. </p>
  
  <p>The code I am using is nearly identical to the documentation code that Microsoft provides for this use case: <a href="https://dev.office.com/reference/add-ins/shared/document.getfileasync#example---get-a-document-in-office-open-xml-compressed-format" rel="noreferrer">https://dev.office.com/reference/add-ins/shared/document.getfileasync#example---get-a-document-in-office-open-xml-compressed-format</a></p>
  
  <p>The server endpoint requires uploads to be POSTed through a multipart form, so I create a FormData object on which I append the file (a blob) as well as some metadata, when creating the $http call.</p>
  
  <p>The file is being transmitted to the server, but when I open it, it has become corrupted and it can no longer be opened by Word.</p>
  
  <p>According to the documentation, the Office.context.document.getFileAsync function returns a byte array. However, the resulting fileContent variable is a string. When I console.log this string it seems to be compressed data, like it should be.</p>
  
  <p>My guess is I need to do some preprocessing before turning the string into a Blob. But which preprocessing? Base64 encoding through atob doesn't seem to be doing anything.</p>
  
  <pre><code>                let sendFile = ( fileContent ) =&gt; {
  
                      let blob = new Blob([fileContent], { type: 'application/vnd.openxmlformats-officedocument.wordprocessingml.document' }),
                          fd = new FormData();
  
                      blob.lastModifiedDate = new Date();
  
                      fd.append('file', blob, 'uploaded_file_test403.docx');
                      fd.append('case_id', caseIdReducer.data());
  
                      $http.post('/file/create', fd, {
                          transformRequest: angular.identity,
                          headers: { 'Content-Type': undefined }
                      })
                      .success( ( ) =&gt; {
  
                          console.log('upload succeeded');
  
                      })
                      .error(( ) =&gt; {
                          console.log('upload failed');
                      });
  
                  };
  
  
                  function onGotAllSlices(docdataSlices) {
  
                      let docdata = [];
  
                      for (let i = 0; i &lt; docdataSlices.length; i++) {
                          docdata = docdata.concat(docdataSlices[i]);
                      }
  
                      let fileContent = new String();
  
                      for (let j = 0; j &lt; docdata.length; j++) {
                          fileContent += String.fromCharCode(docdata[j]);
                      }
  
                      // Now all the file content is stored in 'fileContent' variable,
                      // you can do something with it, such as print, fax...
  
                      sendFile(fileContent);
  
                  }
  
                  function getSliceAsync(file, nextSlice, sliceCount, gotAllSlices, docdataSlices, slicesReceived) {
                      file.getSliceAsync(nextSlice, (sliceResult) =&gt; {
  
                          if (sliceResult.status === 'succeeded') {
                              if (!gotAllSlices) { // Failed to get all slices, no need to continue.
                                  return;
                              }
  
                              // Got one slice, store it in a temporary array.
                              // (Or you can do something else, such as
                              // send it to a third-party server.)
                              docdataSlices[sliceResult.value.index] = sliceResult.value.data;
                              if (++slicesReceived === sliceCount) {
                                  // All slices have been received.
                                  file.closeAsync();
  
                                  onGotAllSlices(docdataSlices);
  
                              } else {
                                  getSliceAsync(file, ++nextSlice, sliceCount, gotAllSlices, docdataSlices, slicesReceived);
                              }
                          } else {
  
                              gotAllSlices = false;
                              file.closeAsync();
                              console.log(`getSliceAsync Error: ${sliceResult.error.message}`);
                          }
                      });
                  }
  
                  // User clicks button to start document retrieval from Word and uploading to server process
                  ctrl.handleClick = ( ) =&gt; {
  
                      Office.context.document.getFileAsync(Office.FileType.Compressed, { sliceSize: 65536 /*64 KB*/ }, 
                          (result) =&gt; {
                              if (result.status === 'succeeded') {
  
                                  // If the getFileAsync call succeeded, then
                                  // result.value will return a valid File Object.
                                  let myFile = result.value,
                                      sliceCount = myFile.sliceCount,
                                      slicesReceived = 0, gotAllSlices = true, docdataSlices = [];
  
                                  // Get the file slices.
                                  getSliceAsync(myFile, 0, sliceCount, gotAllSlices, docdataSlices, slicesReceived);
  
                              } else {
  
                                  console.log(`Error: ${result.error.message}`);
  
                              }
                          }
                      );
                  };
  </code></pre>