各種下載文件方式總結


文件下載有多種方式,鏈接跳轉方式下載,打開新頁面下載,ajax下載文件。

以前ajax是不能下載文件的,現在的xhr2版本支持blob,可以將文件下載到內存中,然后彈出保存框,保存到本地。

這樣不能下載太大的文件,內存會被撐爆。新的fetch Api也可以下載文件。

示例如下:

1. 跳轉下載

function location_download(){
     location.href = '/file/build';
}

2. 超鏈接下載(可自由調整為本頁下載或新開頁面下載)

<a class="btn" download="data.zip" target="_blank" href="/file/build">
   超鏈接直接下載
</a>

3. 模擬超鏈接下載

function simulateA_download() {
    var a = document.createElement('a');
    a.href = '/file/build';
    //文件名無效
    a.download = 'data.zip';
    document.body.appendChild(a);
    a.click()
    document.body.removeChild(a);
}

4. 原生xhr下載

function ajax_download(){
    var url = '/file/build';
    var xhr = new XMLHttpRequest();
    xhr.open('GET', url, true);    // 也可以使用POST方式,根據接口
    xhr.responseType = "blob";  // 返回類型blob
    // 定義請求完成的處理函數,請求前也可以增加加載框/禁用下載按鈕邏輯
    xhr.onload = function () {
        // 請求完成
        if (this.status === 200) {
            // 返回200
            var blob = this.response;
            var reader = new FileReader();
            reader.readAsDataURL(blob);  // 轉換為base64,可以直接放入a表情href
            reader.onload = function (e) {
                // 轉換完成,創建一個a標簽用於下載
                var a = document.createElement('a');
                //文件名有效
                a.download = 'data.zip';
                //會造成跳轉到空白頁,解決方案???
                a.href = e.target.result;
                a.target = '_self';
                document.querySelector("body").appendChild(a);  // 修復firefox中無法觸發click
                a.click();
                a.parentNode.remove();
            }
        }
    };
    // 發送ajax請求
    xhr.send()
}

5. axios下載

function axios_download(){
    let url = '/file/build';
    let fileName = 'data_axios.zip';
    let type = fileName;

    return axios({
        method: 'get',
        url: url,
        responseType: 'blob',
        headers: {
            'content-disposition': `attachment;filename=${type}`,
            'content-type': 'application/x-download;charset=utf-8'
        }
    })
    .then(res => {
        const blob = new Blob([res.data], {type: type})
        const url = window.URL.createObjectURL(blob)
        const link = document.createElement('a')
        link.style.display = 'none'
        link.href = url
        //文件名有效
        link.setAttribute('download', fileName)
        document.body.appendChild(link)
        link.click()
        document.body.removeChild(link)
    })
}

6. superagent下載

function superagent_download(){
    let url = '/file/build';
    let fileName = 'data_super.zip';
    let type = fileName;

    return superagent.get(url)
                        .set('content-disposition', `attachment;filename=${type}`)
                        .set('content-type', 'application/x-download;charset=utf-8')
                        .type('blob')
                        .then(res => {
                        const blob = new Blob([res.data], {type: type})
                        const url = window.URL.createObjectURL(blob)
                        const link = document.createElement('a')
                        link.style.display = 'none'
                        link.href = url
                        //文件名有效
                        link.setAttribute('download', fileName)
                        document.body.appendChild(link)
                        link.click()
                        document.body.removeChild(link)
                    })
                        
}

7. fetch下載

function fetch_download() { 
    //可以先提示'文件下載中...',這樣在下載框彈出之前,用戶體驗會好很多
    var url = "/file/build"; 
    fetch(url).then(res => res.blob().then(blob => { 
        var a = document.createElement('a'); 
        var url = window.URL.createObjectURL(blob);   // 獲取 blob 本地文件連接 (blob 為純二進制對象,不能夠直接保存到磁盤上)
        var filename = res.headers.get('Content-Disposition');
        a.href = url; 
        a.download = filename.split('filename=')[1];
        a.click(); 
        window.URL.revokeObjectURL(url); 
        //提示'下載完成'; 
    })); 
}

 8. 構造form下載

function form_download(values){
    let url = '/file/build';
    try{
        let form = document.createElement('form');
        //用target指向iframe會打開新頁面,原因是?????
        //form.target = 'ifr-down';
        form.action = url;
        form.method = 'get';

        if(values && typeof values == 'object'){
            Object.keys(values).forEach(item => {
                form.insertAdjacentHTML('beforeend', `<input type="hidden" name="${item}" value="${values[item]}"/>`);
            })
        }

        let iframe = document.createElement('iframe');
        iframe.id = 'ifr-down';
        iframe.style = 'display:none';
        iframe.src = "about:blank";
        iframe.onload = function(){
            iframe.onload = null;
            //document.body.removeChild(form);
            //document.body.removeChild(iframe);
        }
        //document.body.appendChild(iframe);
        document.body.appendChild(form);
        form.submit();
    }
    catch(e){
        console.log(e);
    }
}

 

參考:https://www.cnblogs.com/YMaster/p/7707989.html

         https://segmentfault.com/a/1190000022255080

         https://www.jb51.net/article/122797.htm


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM