When I try it in PostMan I can download the file by adding the token to the header. I can't find a way to add the token on the header. Is that something that should be in the frontend or in the backend?
React js
<a
href={process.env.REACT_APP_BACKEND_URL `/files/download/${props.id}`}
rel="noreferrer"
target="_blank"
download
className="download-link"
>
Download File
</a>
Express js:
router.get('/download/:fid', async (req, res, next) => {
const fileId = req.params.fid;
let filePost;
try {
filePost = await File.findById(fileId);
} catch (err) {
return next(new HttpError("Error", 500));
}
console.log(filePost.file);
res.download(filePost.file);
);
CodePudding user response:
You need to use Http Client
to send the token in header.
const handleDownload = async () => {
const res = await fetch(`${process.env.REACT_APP_BACKEND_URL}/files/download/${props.id}`, {
headers: {
token: '<your token>'
}
});
const json = await res.json();
console.log(json.data);
};
<a
onClick={handleDownload}
rel="noreferrer"
target="_blank"
download
className="download-link"
>
Download File
</a>
I strongly suggest you convert a
tag into a button
.
CodePudding user response:
Downloading a resource with pure HTML (an <a>
anchor or a <form>
) produces only requests with "standard" headers like Accept-Language
or Accept-Encoding
, never with a token header. So what you try is impossible with pure HTML.
What you could do it make a request with the Javascript function fetch
and convert the response to a download URL with URL.createObjectURL
. This download URL can then be assigned to an anchor element on which the user can click.
fetch(`${process.env.REACT_APP_BACKEND_URL}/files/download/${props.id}`,
{headers: {...}})
.then(response => response.blob())
.then(function(blob) {
document.getElementById("anchor").href = URL.createObjectURL(blob);
});