← Back Home

Flask Pdf Download

  1. python
  2. flask
  3. pdfkit
  4. wkhtmltopdf

This is a short note on getting PDF downloads working on Flask.

The goal is a button with ‘Download as PDF’:

This seemed easy: just use pdfkit, get the correct dependencies and go. It turns out there were some hiccups for which I needed to combine several answers.

Getting PDFkit to run on a Docker image

I used the following code to get it working. It uses apt-get to get wkhtmltopdf and its dependencies. Then, I patched wkhtmltopdf to make it work headless.

RUN apt-get update
RUN apt-get install -y wkhtmltopdf
RUN wget -nv https://downloads.wkhtmltopdf.org/0.12/0.12.5/wkhtmltox_0.12.5-1.stretch_amd64.deb
RUN apt install -y ./wkhtmltox_0.12.5-1.stretch_amd64.deb
RUN pip install pdfkit

For some reason (there are more people talking about this issue) the headless part does not work out-of-the-box due to some upstream problem of a dependency.

Generate the PDF

import pdfkit
# ...Import other Flask stuff

# Render the HTML
print_html = render_template('print.html')

# Convert the HTML to PDF, as target filename give 'False'
pdf = pdfkit.from_string(print_html, False)

# Convert the bytes to a file(like)
file = io.BytesIO(pdf)

# Optional: add a timestamp to the generated file.
created_on = current_time_local().strftime('%Y-%m-%d %H:%M:%S')
filename = f"Filename ({created_on})"

# Output to the browser
return send_file(file,
                 attachment_filename=filename,
                 mimetype='application/pdf',
                 # Give this argument to let the user stay on the current page
                 as_attachment=True,
                 # Set a low cache timeout
                 cache_timeout=-1)