關於React+SpringMVC+axios前後端分離實現文件下載

 

最近React項目中用到了導出功能,網上搜索一番後決定採用Blob方式(推薦)來實現,現分享下具體實現步驟。

我主要採用後端生成excel文件流返回給前端來實現的,具體代碼如下:

    @RequestMapping(value = "/download")
    public void export(HttpServletRequest request,
            HttpServletResponse resp) {
        HSSFWorkbook book = new HSSFWorkbook();
         try {
             HSSFSheet sheet = book.createSheet("mySheent");
              String[] headers = {"用戶ID", "郵箱賬號","暱稱","年齡","性別","狀態", "註冊時間"};
              HSSFRow row = sheet.createRow(0);
              for (short i = 0; i < headers.length; i++) {
                  //創建單元格,每行多少數據就創建多少個單元格
                  HSSFCell cell = row.createCell(i);
                  HSSFRichTextString text = new HSSFRichTextString(headers[i]);
                  //給單元格設置內容
                  cell.setCellValue(text);
              }
            resp.setContentType("application/vnd.ms-excel;charset=utf-8");
            resp.setHeader("Content-Disposition", "attachment;filename="+ new String(("Excel.xls").getBytes(), "iso-8859-1"));
            book.write(resp.getOutputStream());
        } catch (UnsupportedEncodingException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

這裏需要注意的地方有兩個:

   resp.setContentType("application/vnd.ms-excel;charset=utf-8");
   resp.setHeader("Content-Disposition", "attachment;filename="+ new String(("Excel.xls").getBytes(), "iso-8859-1"));

第一行application/vnd.ms-excel說明將結果導出爲Excel

第二行說明提供那個打開/保存對話框,將文件作爲附件下載

上面就是後臺的全部代碼了,接下來看一下前端的代碼:

//service.js

import { request } from 'utils/request';
export async function exportExcel(params){
    var reqBody = {
        url: "/download",
        method: 'post',
        config:{
            headers: {'Content-Type': 'application/x-www-form-urlencoded'},
            responseType: 'blob',
        },
        data:{
            ...params
       }
    }
    return request(reqBody);
}

這裏爲了方便做記錄,我是直接在頁面中使用axios發送了個post請求。

仔細看axios請求加了個responseType: 'blob'配置,這是很重要的

請求成功後返回了一個Blob對象,你如果沒有正確的加上responseType: 'blob’這個參數,返回的就不是個Blob對象,而是字符串了。

接下來就是將返回的Blob對象下載下來了:

//model.js

import { exportExcel } from 'services/service';

export default {
    namespace: 'softphone',
    state: {
        data:[],
    },
    reducers: {
      search(state, {payload}) {
        //console.log("<<<<<<<<payload:",payload);
        return {...state, ...payload};
      },
    },
    effects:{
        *exportReport({ payload }, { call, put }) {
            try {
                    let response = yield call(exportExcel, payload);
                    console.log('--------------response-------', response);
                    if (response.statusCode === 200) {
                        var blob = new Blob([response.obj], {type: 'application/vnd.ms-excel;charset=utf-8'})
                        var url = window.URL.createObjectURL(blob);
                        var aLink = document.createElement("a");
                        aLink.style.display = "none";
                        aLink.href = url;
                        aLink.setAttribute("download", "用戶列表.xls");
                        document.body.appendChild(aLink);
                        aLink.click();
                        document.body.removeChild(aLink); //下載完成移除元素
                        window.URL.revokeObjectURL(url); //釋放掉blob對象
                    }  
            } catch (error) {
                console.error(error);
            }
        },
    },
  };

以上就是React導出Excel的全部代碼,寫的比較倉促,颱風來了趕緊下班,有問題歡迎留言討論~~~~~

關於service.js中request從哪來的,請參照我上一篇博文https://mp.csdn.net/postedit/98982974

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章