NodeJs / Express编写xlsx-template并将其发送回以供浏览器下载

时间:2019-05-08 19:14:13

标签: node.js http download client

我有这个excel,我想替换标量值作为xlsx-template文档说:

| Extracted on: | ${extractDate} | 我想通过响应对象发送它。该文件已正确写入输出路径中,但在客户端中却给了我二进制输出。贝娄是对Url的后端调用

this.downloadSheet = async (req, res) => {

    let seriesNumber = Number(req.body.seriesNumber);
    let sheetPath = path.resolve('../filePath/excel.xlsx');
    let sheetFinalOuput = path.resolve('../filePath/excelOutput.xlsx');
    #Get data needed to swap for the excel
    let excelDataStream = await ReportService.getBalanceSheetAllInOne(balanceSheetPath, seriesNumber);
    fs.readFile(path.resolve(balanceSheetPath), function(err, data) {
      // Create a template
      let template = new XlsxTemplate(data);

      // Replacements take place on first sheet
      const sheetNumber = 1;

      // Perform substitution
      template.substitute(sheetNumber, excelDataStream);

      // Get binary data
      var mydata = template.generate({ type: 'nodebuffer'});

      fs.writeFile(path.resolve(balanceSheetFinalOuput), mydata, function(err) {
        if(err) {
          return console.log(err);
        }
        console.log(`Wrote data in file, check please!`);

        // Send File & set headers
        res.set({'Content-Disposition': `attachment; filename=balanceIncome${seriesNumber}.csv`, 'Content-Type': 'text/csv'});
        res.write(mydata);
        res.end();
      });
    });
  };

客户端功能http发布请求

$http.post(`${settings.apiHost}/api/panel/report/balanceSheet/allInOne/false`,{seriesNumber: $scope.seriesNumber})
        .success(function (response) {
          var file = new Blob([response], {type: 'text/csv'});

          var isGoogleChrome = window.chrome != null && window.navigator.vendor === "Google Inc.";
          var isIE = /*@cc_on!@*/false || !!document.documentMode;
          var isEdge = !isIE && !!window.StyleMedia;


          if (isGoogleChrome){
            var url = window.URL || window.webkitURL;

            var downloadLink = angular.element('<a></a>');
            downloadLink.attr('href',url.createObjectURL(file));
            downloadLink.attr('target','_self');
            downloadLink.attr('download', `balanceSheet_${$scope.seriesNumber}.csv`);
            downloadLink[0].click();
          }
          else if(isEdge || isIE){
            window.navigator.msSaveOrOpenBlob(file,`balanceSheet_${$scope.seriesNumber}.csv`);

          }
          else {
            var fileURL = URL.createObjectURL(file);
            window.open(fileURL);
          }
        })

1 个答案:

答案 0 :(得分:1)

客户端

const url = `${settings.apiHost}/api/panel/report/balanceSheet/allInOne/false/${$scope.seriesNumber}`;
window.open(url);

服务器端(将路由器参数和方法更改为GET)

let seriesNumber = Number(req.params.seriesNumber);
... 
fs.writeFile(path.resolve(balanceSheetFinalOuput), mydata, function(err) {
  if(err) {
    return console.log(err);
  }
  console.log(`Wrote data in file, check please!`);

  // Send File & set headers
  res.set({'Content-Disposition': `attachment; filename=balanceIncome${seriesNumber}.csv`, 'Content-Type': 'text/csv'});
  res.send(mydata);
});

另一种方式

客户端

...
.success(function (nodeBuffer) {
  let arraybuffer = Uint8Array.from(nodeBuffer).buffer;
  var file = new Blob(arraybuffer, {type: 'text/csv'});
  ....
}

服务器端

...
fs.writeFile(path.resolve(balanceSheetFinalOuput), mydata, function(err) {
  if(err) {
    return console.log(err);
  }
  console.log(`Wrote data in file, check please!`);
  res.send(mydata);
});
...