1. 程式人生 > >js-xlsx實現檔案匯出、下載(excel)

js-xlsx實現檔案匯出、下載(excel)

記錄一下近期使用js-xlsx的一些經驗

真正的.xls\.xlsx檔案,就算是空白的其實是包含了一些內容的

所以並不能直接像寫入txt一樣直接搞一個file往裡面把資料寫入就完了

現在網上查得到匯出excel的一些方法:

1、在IE上使用ActiveXObject匯出檔案

由於我們客戶端是基於chorme的,所以沒有做嘗試

2、匯出csv檔案

如果是比較簡單的表格(沒有表格單元格合併等需求),其實csv檔案也是一個不錯的選擇(當然前提是你不介意這個檔案是csv檔案)。需求比較介意,所以沒有對csv進行嘗試

3、匯出偽.xls\.xlsx檔案

①對html程式碼進行格式化,最後生成一串uri檔案連結,再通過<a>標籤進行下載

      // let uri = 'data:application/vnd.ms-excel;base64,'
      // let template = 
      //   '<html xmlns:o="urn:schemas-microsoft-com:office:office" ' +
      //   'xmlns:x="urn:schemas-microsoft-com:office:excel" ' +
      //   'xmlns="http://www.w3.org/TR/REC-html40"><head>' +
      //   '<!--[if gte mso 9]><xml><x:ExcelWorkbook>' +
// '<x:ExcelWorksheets><x:ExcelWorksheet><x:Name>{worksheet}' + // '</x:Name><x:WorksheetOptions><x:DisplayGridlines/></x:WorksheetOptions>' + // '</x:ExcelWorksheet></x:ExcelWorksheets></x:ExcelWorkbook></xml>' + // '<![endif]--></head><body><table>{table}</table></body></html>'
// let base64 = (s: any) => { // return window.btoa(unescape(encodeURIComponent(s))) // } // let format = (s: any, c: any) => { // return s.replace(/{(\w+)}/g, (m: any, p: any) => { // return c[p] // }) // } // let tableHTML = table[0].innerHTML + table[1].innerHTML // let ctx = { // worksheet: '統計', // table: tableHTML.replace(/<(img).*?>/g, '') // 篩選掉<img> // } // let downloadLink = document.createElement('a') // downloadLink.href = uri + base64(format(template, ctx)) // downloadLink.download = '成績統計.xls' // downloadLink.click()

這種大概可以保留行內樣式,比如字型顏色、字型粗細等,但是對單元格格式進行控制(有些全數字的字串過長會被識別成科學計數法),網上很多說可以用style="mso-number-format:\\@;",嘗試了之後並不可行

②當然還有一種是可以不用對html進行格式化

因為excel可以識別html程式碼,可以跳過方法①中對html進行格式化的步驟,直接將html匯出

<html>
    <head>
        <meta charset="utf-8"/>  //避免中文亂碼
    </head>
    <body>
        <table>
            <tr>
                <th>標題1</th>
                <th>標題2</th>
                <th>標題3</th>
                <th>標題4</th>
            </tr>
            <tr>
                <td>內容1</td>
                <td>內容2</td>
                <td>內容3</td>
                <td>內容4</td>
            </tr>
        </table>
    </body>
</html>

excel也可以展示出來效果,但是開啟之前會提示檔案格式和副檔名不匹配,也就是說,這只是一個披著.xls副檔名的html檔案,所以它連基本的單元格邊框都沒有,除非你在table裡寫上border="1"

 

③另外還有一種,更簡單,直接

 

以上三種方法生成的全是偽xls,因為他們沒有excel檔案裡那7kb內容,所以就算拓展名改成.xls\.xlsx,也只是一個假的檔案

4、使用js-xlsx庫,實現真正的.xls\.xlsx匯出

參考https://github.com/SheetJS/js-xlsx

 ①安裝

npm install xlsx

或者

bower install js-xlsx

②匯入

官方github上有給各種框架的demo:

可以根據專案框架選擇匯入方式,這裡是vue:

import XLSX from 'xlsx' ③使用
      let workbook = XLSX.utils.table_to_book(wholeTable)
      let xls = XLSX.write(workbook, {
        bookType: 'xls',  // 生成的檔案格式
        bookSST: false,   // 是否生成Shared String Table,官方解釋是,如果開啟生成速度會下降,但在低版本IOS裝置上有更好的相容性
        type: 'base64',   // 編碼方式
      })

這裡xlsx提供了多種方法:

寫入:

  • aoa_to_sheet 將JS陣列的陣列([ [...],[...],[...] ])轉換為工作表
  • json_to_sheet 將json物件陣列轉換為工作表
  • table_to_sheet 將DOM TABLE元素轉換為工作表
  • sheet_add_aoa 將JS資料陣列新增到現有工作表中
  • sheet_add_json 將json物件陣列新增到現有工作表中

讀取:

  • sheet_to_json 將工作表物件轉換為JSON物件陣列
  • sheet_to_csv 將工作表轉換成csv
  • sheet_to_txt 生成UTF16格式的文字
  • sheet_to_html 生成HTML輸出
  • sheet_to_formulae 生成公式列表(具有值回退)

單元格和單元格地址操作:

  • format_cell 生成單元格的文字值(使用數字格式)
  • encode_row / decode_row 在0索引行和1索引行之間轉換
  • encode_col / decode_col 在0索引列和列名之間進行轉換
  • encode_cell / decode_cell 轉換單元格地址
  • encode_range / decode_range 轉換細胞範圍

可以說是肥腸強大了