Ubuntu – Server-side print to PDF of HTML file in /tmp

firefoxpdfPHPUbuntuxvfb

I'm working on a project where we need consistent printing of certain pages, and PDFs are made for that. The customers also like to have some local copies, so this would be a two-fold win. Things get really precarious in printing as far as where page breaks end up and how padding effects things.

What I want to do:

  1. User is viewing a page
  2. User requests a PDF
  3. PHP generates a HTML file, pretty much the site minus the wrapper and plus CSS
  4. PHP stores that to /tmp/foobar.html
  5. PHP executes a command that prints to PDF, similar to firefox --display=:1 -print /tmp/foobar.html -printmode pdf -printfile /tmp/foobar.pdf
  6. PHP uploads that PDF to Amazon S3 for permanent storage, adds into our database for future reference

What I've tried:

I've installed Firefox on my server and Xvfb. I've tried setting up Xvfb to be a virtual display and have Firefox run on it, but I get Xlib: extension "RANDR" missing on display ":1". no matter what I do. It's probably misconfigured, I did try adding that extension when starting the new screen with no luck. I'm not sure if I'm not going about this the right way. If Firefox and Xvfb are the right route, what's the proper way to get them to talk to eachother? Are there more dependencies? I'll elaborate on this if it turns out to be the right path.

What I don't want to do:

No native PHP converters – Lots of nested tables in this HTML, lots of floats, lots of stuff native PHP doesn't handle well. I've tried all 3 already.

I could so easily do this on a Windows server, but I'd rather keep costs down. Plus then I'd have to set up cross-server communications, which will slow things down a bit

TL:DR; I'm trying to print to PDF using Firefox running on a server with no display so I can have a consistent print experience. I've tried Xvfb and I've almost given up. If this is the correct way, how do I configure Xvfb? Otherwise, how else would I go about doing this?

Best Answer

Use a headless renderer like PhantomJS or wkhtmltopdf.

Related Topic