Previously, because of laziness, the download of asynchronous requests was written directly in the a tag, and the request permission let the backend make special processing judgment, like this
<a href="getRequestUrl">Click to download</a>
Now I don't think it's very good. One is that the back-end permission needs to be judged separately. The other is that if the calling interface reports an error, it can't be handled. After the research, I modified it. The project uses the lib of axios, so I modified the request and response of axios. However, for the native writing method and other libraries, the principle is the same.
1. Set the responseType of the request to blob
function exportData(p) { return axios({ url: '/data/export', method: 'get', params: p, responseType: 'blob' }); }
2. Handle the response
Because the response interceptor is used to process the response in the project, I have done the processing in the interceptor, or I can handle it alone.
axios.interceptors.response.use( response=> { // ... // Blob type processing let checkType = response.config.responseType; if(checkType === "blob" && res.type === 'application/octet-stream') { // Directly return response data during normal download return response.data } else if(checkType === "blob" && res.type === 'application/json') { // When an error occurs in the request, the interface returns json, so the content in the blob is taken out. let reader = new FileReader(); reader.onload = function(event){ let content = reader.result; // Content in blob Message({ message: JSON.parse(content).desc, type: 'error', duration: 5 * 1000 }) }; reader.readAsText(response.data); return Promise.reject('error') } // ... }, error => { // ... } )
3.html page starts to download automatically
exportData(para).then(res => { let content = res; let aTag = document.createElement('a'); let blob = new Blob([content]); aTag.download = 'Datas.xlsx'; // You can also let the backend set the file name and return it through headers. aTag.href = URL.createObjectURL(blob); aTag.click(); URL.revokeObjectURL(blob); }).finally(() => { })
Reference blog: https://www.cnblogs.com/coder...