Download Files In The Background & Show Realtime Progress Bar using Django and Vue JS

Md Mahmudul Huq Topu
3 min readFeb 27, 2023

--

Today we will see how to send files in API without exposing the file’s main path (media path) using Django rest framework with the help of Content Disposition header information. Also in VueJS will call the API, download the file from the response in the background and show Realtime percentage in the progress bar.

Why we need this?
Normally we put file path in an anchor tag to let users download files. But what if they copy the link and share ? So sharing real location and file names is not a good idea if you need protection. So we will send the file in api response and also will change the filename keeping the original extention using Content Disposition technique.

Here is the backend code in Django

In the above code we are getting the file from a simple model haivng name and file field only. In line 18 we are reading the file and in line 18 we are extracting the file extention.
As we need a new file name while downloading, so we used UUID (8 digit) and concat with file name from model in line 20.
As discussed we need to send a Httpresponse where the file object “file_data” from line 18 with content type to force download.

response['Content-Disposition'] = "attachment; filename=" + slugify(new_file_name) + '.' + ext

Each HTTP response can send header information with content disposition so here we path a string where first part is the attachment, second part seprated by ; is the filename (newly generate name).
Lastly , we need to expose the header information to the client as by default client can’t access this directly until and unless specified explicitly.

Here is the frontend part in Vue Js

In the above code, we are sending a post request where post body is “file_id” and response type blob object as we are accepting file response.
In Axios we onDownloadProgress where we can get the progess of the event triggered.
So we calculated simply by using the formula
Math.round((progressEvent.loaded * 100) / progressEvent.total)
and we are setting the value to the data property.
As this is a promise based request, so in then block, we are getting the filename in line 70 removing all white spaces.
To force download a temporary element (anchor tag) is created in the dom, then in 76 we have set the file url which the the blob response.
We know by putting download attribute on the anchor tag will enable force download.
Finally we are appenfing the element on the fly to the body and clicking robotically using link.click(). So file will be download and progress bar will show report.

Have a look at the network tab and headers information

In bootstrap, we just need to change the value of :style=”’width: ‘+percentCompleted+’%;’” propery in bootstrap progress bar.

--

--

Md Mahmudul Huq Topu
Md Mahmudul Huq Topu

Written by Md Mahmudul Huq Topu

I’m a Full Stack Software Engineer at Skill Jobs.Also do youtubing(Metacentric Bangladesh) since 2014.

No responses yet