Alaa
Alaa

Reputation: 167

Axios download file with original right extension

I have below vuex method for download file :

   downloadFile(context, url) {
      return new promise((resolve, reject) => {
        const method = "GET";
        axios
          .request({
            url: url,
            method,
            responseType: "blob"
          })
          .then(response => {
            let fileURL = window.URL.createObjectURL(
              new Blob([response.data]),
              {
                type: response.headers["content-type"]
              }
            );
            let fileLink = document.createElement("a");
            fileLink.href = fileURL;
            let fileName = response.headers["content-disposition"].split(
              "filename="
            )[1];
         
            fileLink.setAttribute("download", fileName);
            document.body.appendChild(fileLink);

            fileLink.click();
            fileLink.remove();
            resolve();
          })
          .catch(() => {
            reject();
          });
      });
    }

I pass the URL link (getting from laravel API)

Blockquote

the problem that the file always downloaded with txt extension

Blockquote

There is any method to get the file extension? enter image description here

Upvotes: 2

Views: 3084

Answers (2)

Dan
Dan

Reputation: 63119

Your server didn't send the file extension in the screenshot. If it's not in downloadFile's url argument and you can't fix your server response to include it, you could deduce it from Content-Type. You could create a hash linking each content type to an extension.

Remove this:

let fileName = response.headers["content-disposition"].split(
   "filename="
)[1];

Replace it with this to capture the extension:

const extensions = {
  'application/vnd.openxmlformats-officedocument.wordprocessingml.document': 'docx',
  'application/fake': 'fake', // Just an example
  // etc. Add another line for every Content-Type
}
const contentType = response.headers["Content-Type"];
const extension = extensions[contentType];
const filename = 'file.' + extension;

This will name every file "file.<extension>"

Upvotes: 2

Adam Orłowski
Adam Orłowski

Reputation: 4484

If your endpoint does not supply the extension you can add it in the fileName. So it could be:

-  fileLink.setAttribute("download", fileName);
+  const extention = 'pdf'; // example
+  fileLink.setAttribute("download", `${fileName}.${extention}`);

Upvotes: 0

Related Questions