【问题标题】:wkhtmltopdf error when generating pdf with lots of pages with header / footer生成包含大量页眉/页脚页面的 pdf 时出现 wkhtmltopdf 错误
【发布时间】:2014-08-18 02:46:23
【问题描述】:

我正在使用 pdfkit(在后台使用 wkhtmltopdf)在我的 rails 应用程序中生成 PDF。遵循指南here 我已经得到它主要适用于PDF的基本案例。我现在在尝试生成包含大量页眉/页脚的 PDF 时遇到了问题。尝试生成 PDF 时,我在控制台中从 wkhtmltopdf 看到的错误是:

QEventDispatcherUNIXPrivate(): Unable to create thread pipe: Too many open files
QEventDispatcherUNIXPrivate(): Can not continue without a thread pipe

可用于重新创建错误的 html 的最小示例:

<!-- content of pdf_header_url is the character "h" -->
<meta content="<%= pdf_header_url %>" name="pdfkit-header-html"/>
<!-- content of pdf_footer_url is the character "f" -->
<meta content="<%= pdf_footer_url %>" name="pdfkit-footer_html"/>
<% [*1..3].each do |j|%>
  <h1><%= j %></h1>
  <ul>
    <% [*1..1000].each do |i|%>
      <li><%= i %></li>
    <% end %>
  </ul>
<% end %>

请注意,删除页眉/页脚标签可以使 pdf 呈现良好。

生成 PDF 的实际 ruby​​ 代码是:

def view_report
  html = render_to_string(:template => 'pdf/pdf_body.html', :layout => false)
  kit = PDFKit.new(html)
  pdf = kit.to_pdf
  send_data pdf, :type => 'application/pdf', :disposition => 'inline', :filename => 'foo.pdf'
end

访问此控制器路由将生成 PDF。最后,我还有一个用于页眉/页脚的控制器,因为这些“部分”需要通过 url 获取:

class PdfController < ApplicationController

  def header
    render :layout => false
  end

  def footer
    render :layout => false
  end

end

为了一个最小的可重现示例,pdf_header_url 和 pdf_footer_url 的值实际上只是“h”和“f”。

是否有熟悉 wkhtmltopdf 的人对解决此问题的进一步调试步骤有任何建议?

【问题讨论】:

  • 您能否展示您用于生成 PDF 的所有代码?以及pdf_header_urlpdf_footer_url 的值。我想尝试重现这个。

标签: ruby-on-rails ruby qt wkhtmltopdf


【解决方案1】:

我今天收到了同样的错误消息,我用一个非常简单的解决方案解决了这个问题。问题是我的页眉和页脚需要是带有 html、head 和 body 标签的完整 html 文档。另外,看看您是否可以获得生成的页眉和页脚的 html 输出并验证它们。

【讨论】:

  • 很好奇,知道为什么这可以解决问题吗?
  • 我无法查看源代码,但我的假设是任何 HTML 入口点都需要是完整、正确的 HTML 文档。文档的正文是 HTML 入口点,需要是完整的格式良好的 HTML 文档,如果页眉和页脚的行为方式相同,它们也应该是完整的 HTML 文档。就像我说的,尚未在消息来源中确认,只是一种强烈的预感并致力于测试。
  • 感谢您的回复。所以,我遇到了这个问题,页眉和页脚文件都是完整的 HTML 文件。我要通过的问题是提高服务器上的“ulimit -n”,类似于@ashkulz 所指的。我将发布一个包含更多详细信息的答案,以帮助其他遇到此问题的人。
【解决方案2】:

打开文件限制。

我确保我的页眉和页脚文件是完整的 HTML 文档,正如 Tom Hirschfeld 建议的那样,但我仍然收到打开文件过多的错误。

搜索互联网后,我发现您需要提高单个进程允许打开的文件数量的限制。就我而言,我正在生成具有数百到数千页的 PDF。它在没有页眉和页脚的情况下工作得很好,但是当合并页眉和页脚时,它似乎达到了这个打开文件的上限。

根据您正在运行的系统,有不同的方法可以调整此设置,但以下是在 Ubuntu 服务器上对我有用的方法:

将以下内容添加到 /etc/security/limits.conf 的末尾:

# Sets the open file maximum here.
# Generating large PDFs hits the default ceiling (1024) quickly. 
*    hard nofile 65535
*    soft nofile 65535
root hard nofile 65535 # Need these two lines because the wildcards
root soft nofile 65535 # (the * above) are not applied to the root user.

ulimit 命令的一个很好的参考可以找到here

我希望这能让一些人走上正轨。

【讨论】:

    【解决方案3】:

    wkhtmltopdf 每页使用 2 个文件描述符(页眉和页脚各一个),这是生成每页自定义变量所必需的。您必须编辑/etc/security/limits.conf 以将nofile(即打开文件的最大数量)设置为适当的高数字——可能需要进行一些实验才能找到适合您的值。

    【讨论】:

    • 感谢您的指点。我添加了另一个答案,其中包含有关我如何具体解决它的更多详细信息。只是想给你一个快速的大拇指。
    猜你喜欢
    • 2017-04-21
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-01-28
    • 1970-01-01
    • 1970-01-01
    • 2015-04-03
    相关资源
    最近更新 更多