使用Node.js中的动态生成的HTML将PDF文件流式传输到浏览器

时间:2017-11-17 04:54:13

标签: node.js express pdf heroku node-html-pdf

好的,我在这里看到了这个问题的几个版本,但我认为我的其他版本比其他版本更深一些,我看不出令人满意的答案。

我想要的:

我在网站上有一个页面,其内容经常被用户更改,我希望他们点击“生成PDF”的按钮,并能够在页面成为一个漂亮的PDF报告。

我尝试使用NodeJS,Express,在Heroku上进行部署。

一般来说,这就是我试图实现这个目标的方式:

我的计划:

  1. 发起GET请求
  2. 查询数据库以获取相关结果
  3. 将数据加载到EJS模板
  4. 保存生成的HTML
  5. 使用npm模块HTML-pdf将其流式传输到浏览器
  6. 其他重要细节:

    1. 这个文件是短暂的。我不想保存它 任何地方。
    2. 我不想在任何地方写它,因为它只是 意味着当时存在于浏览器中。
    3. 此应用程序部署在Heroku上,需要在其中运行 结构体。我不想使用像S3那样的文件存储。
    4. 我的代码:

      router.get('/formulas/:id/pdf', function(req, res){
        var db = req.db.collection('users');
        var id = new ObjectID(req.params.id);
        var pointer = {"formulas.$": 1, "_id": 0};
      //query database, get the info out
      db.aggregate([
        {$match: {"formulas.f_id": id}},
        {$unwind: "$formulas"},
        {$match: {"formulas.f_id": id}},
        {$project : {"formulas": 1, "_id": 0}}
      ]).toArray(function(e, doc){
        if (e) {
        throw e;
      } else {
        var html = null;
        ejs.renderFile('./views/pdf.ejs', { //create template from db query
          project: doc[0].formulas,
          title: 'Formula Info Report',
          description:  'PDF Report For Your Formula by Nutraceutical Pro',
          ID: 'pdf',
          keywords: 'PDF, PDF generator, Formula Info Report',
          user: req.user,
          loggedIn: req.isAuthenticated()
        }, function(err, results){
          if (err) {
            console.log(err);
            }
            html = results; //save results of HTML output
          });
          var options = { format: 'Letter' };
          var path = './public/pdf/formula-' + req.params.id + '.pdf';
          pdf.create(html, options).toStream(function(err, stream) {//initiate stream
            if (err) {
              return console.log(err);
            }
            if (stream) {
              console.log(stream);
              stream.pipe(fs.createWriteStream(path));
              console.log("the pdf was streamed.");
              res.end();
              }
            });
          }
        });
      });
      

      我使用AJAX调用启动GET请求,如下所示:

       $('.getPDF').click(function(){
         var filepath = 'https://my-domain.herokuapp.com/pdf/formula-' + this.id + '.pdf';
       $.ajax({
         url: '/formulas/'+ this.id +'/pdf',
         type: 'GET',
         success: function () {window.open(filepath);}
       });
      

      当我运行脚本时,我会生成一个流,然后控制台会记录创建的PDF。如果我只是将生成的文件保存到我的本地系统,它会很好,但在我的应用程序中,我收到以下错误消息:

      Cannot GET /pdf/formula-59cc38992fb99b00045832ad.pdf
      

      因此,它就像正在创建PDF的原始资料一样,但它没有以允许应用程序读取它的方式记录和创建。

      我愿意接受各种各样的解决方案,所以如果有更简单的方法可以做到这一点,那我就是全部的耳朵。我喜欢坚持使用当前的堆栈。

0 个答案:

没有答案
相关问题