在 Rails 上使用 PDFkit 下载 PDF 时出错

Downloading PDF's using PDFkit error on Rails

我正在尝试将 Rails5 中的 HTML 视图下载为 PDF,但是,每当我下载 PDF 时,我都会收到错误消息:无法加载 PDF 文档。我正在使用以下 gems:

gem 'pdf kit' gem 'wkhtmltopdf-binary'

这是我的控制器:

class InputController < ApplicationController

def index
    @inputs = Input.all
end


def show
    @input = Input.find_by(id: params[:id])

            send_data @pdf, :filename => @input.company + ".pdf",
                                    :type => "application/pdf",
                                    :disposition => "attachment"
end


end

当我输入下载内容时 URL 即:localhost:3000/input/1.pdf 我下载的 pdf 文件有错误:

我的show视图很简单:

<ul>
<li><%= @input.company %></li>
<li><%= @input.position %></li>
<li><%= @input.date %></li>
</ul>

如有任何帮助,我们将不胜感激。

最好的, 阿亚兹

更新

我也刚刚尝试取出@pdf并放入@input:

    def show
    @input = Input.find_by(id: params[:id])
            send_data @input, :filename => @input.company + ".pdf",
                                    :type => "application/pdf",
                                    :disposition => "attachment"
    end

结果无变化

您的代码没有为实例变量分配任何内容 @pdf:

def show
  @input = Input.find_by(id: params[:id])

  send_data @pdf, :filename => @input.company + ".pdf",
                  :type => "application/pdf",
                  :disposition => "attachment"
end

并且实例变量的默认值为 nil。您需要执行以下操作:

input = Input.find_by(id: params[:id])

html = %Q{
<ul>
<li>#{input.company}</li>
<li>#{input.position}</li>
<li>#{input.date}</li>
</ul>
}

kit = PDFKit.new(html, :page_size => 'Letter')
pdf = kit.to_pdf


send_data pdf, :filename => input.company + ".pdf",
               :type => "application/pdf",
               :disposition => "attachment"

或者,如果您想通过 ERB 引擎 运行 读取视图文件,如下所示:

file_path = File.expand_path("../views/input/show.html.erb", __FILE__)
erb_template = File.read(file_path)

@input = Input.find_by(id: params[:id])
renderer = ERB.new(erb_template)
html = renderer.result()

#As above...

来自Rails Guide

By default, controllers in Rails automatically render views with names that correspond to valid routes.
...
...
The rule is that if you do not explicitly render something at the end of a controller action, Rails will automatically look for the action_name.html.erb template in the controller's view path and render it.

并且来自 send_data() 的文档:

This method is similar to render plain: data, but also allows you to specify whether the browser should display the response as a file attachment (i.e. in a download dialog) or as inline data

因此,当您在控制器中调用 send_data() 时,您正在显式渲染某些内容,因此 action_name.html.erb 文件的默认渲染不会发生。