ruby-on-railspdfwicked-pdfcombine-pdf

WickedPDF generating blank pdfs when attempting to render multiple pdfs


I am using WickedPDF in a Rails 6 project to generate PDFs from HTML, and then combine them with prefilled PDF forms. The WickedPDF generated PDFs are split into two sections, each of which must be combined with a form. The forms must appear at the beginning of their respective sections.

I have attempted to generate two PDFs with WickedPDF and then combine them with the prefilled forms using combine_pdf in the appropriate order.

The render_ar_docs and render_gl_docs both work as expected when I visit their routes individually: they generate and save the expected PDF. However, when I call them sequentially in the print_complete_docs action, the resulting PDFs are a single blank page.

How can I generate multiple PDFs from a single action?

Thank you for your help.

def print_complete_docs
    @policy.fill_and_save_acord28
    @policy.fill_and_save_acord25
    render_ar_docs
    render_gl_docs
    pdf = CombinePDF.new
    pdf << CombinePDF.load("tmp/acord28.pdf")
    pdf << CombinePDF.load("tmp/ar_docs.pdf")
    pdf << CombinePDF.load("tmp/acord25.pdf")
    pdf << CombinePDF.load("tmp/gl_docs.pdf")
    pdf.save "tmp/complete_docs.pdf"
    send_file("#{Rails.root}/tmp/complete_docs.pdf", filename: "tmp/#{@policy.legal_vesting} Complete Docs.pdf", type: 'application/pdf')
  end

  def render_ar_docs
    render pdf: 'ar_docs', 
           layout: 'document',
           save_to_file: Rails.root.join('tmp', "ar_docs.pdf"),
           save_only: true
  end
  
  def render_gl_docs
    render pdf: 'gl_docs', 
           layout: 'document',
           save_to_file: Rails.root.join('tmp', "gl_docs.pdf"),
           save_only: true
  end

Solution

  • My issue seems to be related to trying to render multiple times in a single request, which Rails does not allow. Instead I should have used WickedPDF's pdf_from_string method.

    My new (over verbose and un-refactored, but functional) method looks like this:

    def print_complete_docs
        @policy.fill_and_save_acord28
        @policy.fill_and_save_acord25
        render_ar_docs
        render_gl_docs
        
        pdf = CombinePDF.new
        pdf << CombinePDF.load("tmp/acord28.pdf")
        pdf << CombinePDF.load("tmp/ar_docs.pdf")
        pdf << CombinePDF.load("tmp/acord25.pdf")
        pdf << CombinePDF.load("tmp/gl_docs.pdf")
        pdf.save "tmp/complete_docs.pdf"
        send_file("#{Rails.root}/tmp/complete_docs.pdf", filename: "tmp/#{@policy.legal_vesting} Complete Docs.pdf", type: 'application/pdf')
      end
      
      def render_ar_docs
        ar_docs = WickedPdf.new.pdf_from_string(
          render_to_string(
            'policies/ar_docs.html.erb',
            layout:'document.html.erb',
            locals: { policy: @policy }
          ),
          layout: 'document.html.erb'
        )
        save_path = Rails.root.join('tmp','ar_docs.pdf')
        File.open(save_path, 'wb') do |file|
          file << ar_docs
        end
      end
    
      def render_gl_docs
        gl_docs = WickedPdf.new.pdf_from_string(
          render_to_string(
            'policies/gl_docs.html.erb',
            layout:'document.html.erb',
            locals: { policy: @policy }
          ),
          layout: 'document.html.erb'
        )
        save_path = Rails.root.join('tmp','gl_docs.pdf')
        File.open(save_path, 'wb') do |file|
          file << gl_docs
        end
      end
      
    

    PS: Thanks to @Unixmonkey for trying to help, and for his contributions to WickedPDF!