With the development of front-end technology, more and more business scenarios require front-end to handle file downloads. Among the many methods, downloading through the download attribute of the <a>
tag is a common and relatively simple method.
The conventional <a>
tag implements link jump through href. If you only want to download the file instead of jumping to preview, the best way is to add the download
attribute in the <a>
tag, and the download operation can be easily realized.
download
is a new attribute of the <a>
tag in HTML5. This attribute will force the download operation to be triggered, instructing the browser to download the URL instead of navigating to it, and prompt the user to save it as a local file, for example:
<a href=result.png download>download</a>
If the download
attribute is missing, clicking download will directly change to the preview image. When download
attribute is added, the download of the image will be triggered.
The current compatibility of the download
attribute is as shown in caniuse:
It can be seen that most mainstream browsers basically support the download
attribute, and IE's performance is as impressive as ever. Currently, many Window systems still use IE, which is also something that many business needs need to consider. This compatibility issue limits the wider application of download
.
Faced with some business scenarios of dynamic content downloading, that is, the addresses of resources such as pictures are not fixed (such as pictures generated by some online drawing tools), only using HTML cannot meet the needs. In order to satisfy different URL downloads, a method of dynamically triggering URL downloads can be implemented through JS.
function download(href, filename='') { const a = document.createElement('a') a.download = filename a.href = href document.body.appendChild(a) a.click() a.remove() }
It should be noted that appendChild
and remove
operations performed on the created <a>
in the code are mainly for compatibility with the FireFox browser. When calling this method under the FireFox browser, if you do not add the created <a>
tag to the body, click The link will do nothing and trigger a download, which is not the case in Chrome.
The above method can realize the download of same-origin resources. But in many scenarios, cross-domain resources also need to be processed. Unfortunately, the download
attribute currently only applies to same-origin URLs . That is, if the resource address to be downloaded is cross-domain, the download
attribute will be invalid and clicking the link will turn into a navigation preview.
Test: Click to download, the result is only a preview and the image cannot be downloaded.
Note: Chrome 65 previously supported the download
attribute to trigger cross-domain downloads of files. Later, it strictly followed the same-origin policy and could no longer trigger the download of cross-domain resources through download
attribute. FireFox has not supported the download
attribute of cross-domain resources.
The download
attribute can not only trigger downloads, but also specify the download file name:
<a href=test.png download=joker.png>Download</a>
If the suffix of the downloaded file is consistent with the source file, you can set the default file name:
<a href=test.png download=joker>Download</a>
The author once encountered a problem. The cross-domain resource download was triggered through the <a>
tag. The code was basically the same as the download method mentioned above, except that the place where download
attribute was set was slightly different:
a.setAttribute(download, true)
As a result, the following situation occurred in the old version of Chrome browser.
The download file name becomes true
. Obviously, the browser reads the download
attribute value as the file name.
After analysis, the above problems are mainly due to:
1. First of all, download
should not be set to true
. The attribute value of download
is different from disabled
. It is directly related to the file name. And for this front-end and back-end responsive downloading method, the download
attribute is not necessary.
2. Earlier versions of Chrome not only supported the download
attribute of cross-domain resources, but also could reset the file names of cross-domain resources through download
, so the above situation occurred.
The business scenario in which the front-end and back-end cooperate to complete file download is generally implemented by the back-end setting Content-Disposition
information in the response header.
In the HTTP scenario, the first parameter of Content-Disposition is either inline (the default value, indicating that the message body in the reply will be displayed as part of the page or the entire page), or attachment (meaning that the message body should be downloaded to the local ; Most browsers will present a save as dialog box, prefilling the value of filename with the downloaded file name).
If Content-Disposition
is set in the response header and the front end also adds the download
attribute to the <a>
tag of the corresponding link, then the naming rules at this time are:
If the Content-Disposition attribute in the HTTP header is assigned a file name that is different from this attribute, the HTTP header attribute takes precedence over this attribute.
After testing, it was found that when Content-Disposition
in the HTTP header is not empty:
In the Chrome browser, no matter whether the first parameter of Content-Disposition
in the HTTP header is set to attachment or inline , download
cannot reset the file name as long as filename is set. On the contrary, when filename is empty, the download
attribute value will be set to the file name. In the FireFox browser, the browser will only read the filename value of Content-Disposition
. If filename is empty, the source file name will be taken. At this time, download
cannot reset the file name anyway.
To summarize: If the Content-Disposition
information is not set in the response header (for example, the same-origin URL that generally directly locates the resource), the download
attribute can reset the file name. If the backend has set filename in the Content-Disposition
field, the filename value shall prevail.
What should I do if I still want to reset the file name when the file name has been set on the backend?
Blob: URL There is also an introduction to the download
attribute:
Although the HTTP URL needs to be in the same origin, you can use blob: URL and data: URL to make it easier for users to download content generated using JavaScript (such as photos created using an online drawing web application).
Blob
(Binary Large Object) is a binary large object. We are not unfamiliar with this. Some databases use Blob to represent the field type that stores binary files. The File interface is also based on Blob, inheriting the functions of Blob and extending it to support files on the user system. Blob objects are created using the Blob constructor:
Blob(blobParts[, options])
var debug = {hello: world};var blob = new Blob([JSON.stringify(debug, null, 2)], {type : 'application/json'});
If you need to download some simple text or JS string files, you can convert the text information into a blob binary stream, generate a Blob URL, and use the download
attribute to complete the download. The code is as follows.
const downloadText = (text, filename = '') { const a = document.createElement('a') a.download = filename const blob = new Blob([text], {type: 'text/plain'}) // text refers to the text or string content that needs to be downloaded a.href = window.URL.createObjectURL(blob) // A URL string similar to blob:http://localhost:8080/d3958f5c-0777-0845-9dcf-2cb28783acaf will be generated document.body.appendChild(a) a.click() a.remove()}
What is the difference between this Blob URL and the common HTTP URL?
Blob URL/Object URL is a pseudo-protocol that allows Blob and File objects to be used as URL sources such as images and binary data download links.
The browser creates a special reference to the Blob or File object internally through URL.createObjectURL()
. The generated Blob URL can only be used in a single instance of the browser and in the same session, and this URL object will be used when the page exits. Released by the browser.
Therefore, the Blob URL cannot point to a server resource and you cannot open it in other pages. At the same time, due to differences in encoding formats, Blob URLs occupy less space resources and perform better than Data URLs.
Blobs provide a very useful feature for web development: creating blob URLs. Encapsulate the binary data into a Blob object, and then use URL.createObjectURL()
to generate a Blob URL. Since the Blob URL itself is a same-origin URL, you can use this URL with download
to solve the problem of downloading and naming cross-domain resources.
Blob and Fetch can solve the problem of cross-domain and file naming: use fetch
to obtain cross-domain resources, return a blob object and generate a Blob URL, and use download
attribute of the <a>
tag to trigger the download. The code is as follows:
function download(href, filename = '') { const a = document.createElement('a') a.download = filename a.href = href document.body.appendChild(a) a.click() a.remove() }function downloadFile(url, filename='') { fetch(url, { headers: new Headers({ Origin: location.origin, }), mode: 'cors', }) .then(res => res.blob()) .then(blob => { const blobUrl = window.URL.createObjectURL(blob) download(blobUrl, filename) window.URL.revokeObjectURL(blobUrl) })}
At this point, click Download again, and the cross-domain images can be downloaded to the local area normally.
It should be noted that the server where the cross-domain resources are located needs to be configured with Access-Control-Allow-Origin
information, otherwise you will get an uppercase cross-domain error. Header configuration example:
//Allow any domain name to access header('Access-Control-Allow-Origin: *'); //Specify domain name to access header('Access-Control-Allow-Origin: https://h5.ele.me');
There are still some shortcomings in this method. For example, the browser will limit the size of Blob data to no more than 500M, and it will also be insufficient in terms of performance.
Summarize Currently, there are many download methods on the front end, and download
attribute download is one of the simpler ones. However, careful consideration of some of these features can also reveal a lot of useful information. download
is closely related to browser features. At present, the compatibility of this attribute is also a big problem. However, even Microsoft officials implore users not to use IE anymore. I believe that the compatibility problem of download
will continue to be improved in the future, and the application prospects will become more and more popular. broad.
The above is the entire content of this article. I hope it will be helpful to everyone’s study. I also hope everyone will support VeVb Wulin Network.