Situation: You need to download a pdf file (or any file type) from firebase storage to your computer via browser that has a vue.js web app (contains vuetify). You have looked at the firebase storage doc, but it isn't crystal clear. You are not sure about the right firebase storage rules for you. This is for frontend - the user's browser. How shall you implement this?
1 Answers
This is a compilation answer on how to download files from firebase storage to user's computer via a vue web app. The firebase storage download documentation has 90% of what you need for your vue.js web app to download a file to your computer. Follow the steps there. If you are not using firebase authentication, then you might want to set read access to everyone. By default, only authenticated users can read and write. You can do so like this in your firebase storage rule:
rules_version = '2';
service firebase.storage {
match /b/{bucket}/o {
match /{allPaths=**} {
allow read: if request.auth == null;
allow write: if request.auth != null;
}
}
}
This lets anyone view/download your files. Next, by following the guide posted above, you will be able to get the url of the file, then convert it into 'blob' format. Now, the guide doesn't tell you what to do next but another Stack Overflow answer has the solution. I have combined the two here. Basically what happens in the code is:
- You should call the event handler function from
@click.prevent
event emitter instead of@click
. - The event handler function does several things. Like the firebase storage documentation, it gets the url of your file and converts it into a 'blob' via XMLHttpRequest().
- Following the linked solution, you should create a new
a
element, then assign itshref
attribute to the 'blob', download name and emit theclick
event. Revoke thehref
attribute after to avoid accidents.
Traditionally, we use a
links to download files but we can use v-btn
as we are creating the a
link in the event handler. My button has a tooltip and icon. Also, due to linter I removed unuses variables.
Inside html template:
<v-tooltip top>
<template v-slot:activator="{ on, attrs }">
<v-btn
:color="counterThemeColorClass"
fab
ripple
v-bind="attrs"
v-on="on"
@click.prevent="downloadResumePdf"
>
<v-icon
:color="themeColorClass"
x-large
>mdi-file-account-outline</v-icon>
</v-btn>
</template>
<span class="font-weight-bold">download resume</span>
</v-tooltip>
Inside script:
downloadResumePdf() {
const resumeRef = firebase.storage()
.ref('tenzin_resume.pdf');
resumeRef.getDownloadURL().then((url) => {
// `url` is the download URL
console.log(url);
// This can be downloaded directly:
const xhr = new XMLHttpRequest();
xhr.responseType = 'blob';
xhr.onload = function () {
const blob = xhr.response;
const link = document.createElement('a');
link.href = URL.createObjectURL(blob);
link.download = 'tenzin_resume';
link.click();
URL.revokeObjectURL(link.href);
};
xhr.open('GET', url);
xhr.send();
}).catch((error) => {
// Handle any errors
switch (error.code) {
case 'storage/object-not-found':
// File doesn't exist
break;
case 'storage/unauthorized':
// User doesn't have permission to access the object
break;
case 'storage/canceled':
// User canceled the upload
break;
case 'storage/unknown':
// Unknown error occurred, inspect the server response
break;
default:
break;
}
});
},

- 75
- 1
- 10