Django WeasyPrint Integration

2.5.0 · active · verified Thu Apr 16

django-weasyprint is a Django application that integrates WeasyPrint, allowing developers to generate PDF documents from HTML and CSS templates within their Django projects. It provides class-based views and response classes to streamline the process of converting rendered Django templates into PDF files. The current version is 2.5.0, with a release cadence tied to major WeasyPrint and Django releases, supporting modern Python and Django versions.

Common errors

Warnings

Install

Imports

Quickstart

This quickstart demonstrates how to create a basic PDF view for a Django model using `django-weasyprint`. It defines a `Product` model, a `ProductDetailView` for regular HTML display, and a `ProductPDFView` that extends it with `WeasyTemplateResponseMixin` to render the same content as a PDF. Ensure `STATIC_ROOT` and `STATIC_URL` are configured in your Django settings for CSS to be applied correctly, and that WeasyPrint's system dependencies are installed.

import os
from django.db import models
from django.shortcuts import render
from django.urls import path
from django.views.generic import DetailView
from django_weasyprint.views import WeasyTemplateResponseMixin, WeasyTemplateResponse

# models.py (example)
class Product(models.Model):
    name = models.CharField(max_length=255)
    description = models.TextField()
    price = models.DecimalField(max_digits=10, decimal_places=2)

    def __str__(self):
        return self.name

# views.py
class ProductDetailView(DetailView):
    model = Product
    template_name = 'products/product_detail.html'
    context_object_name = 'product'

class ProductPDFView(WeasyTemplateResponseMixin, ProductDetailView):
    # PDF-specific settings
    pdf_stylesheets = [
        os.path.join(os.environ.get('STATIC_ROOT', ''), 'css/pdf_styles.css')
    ]
    pdf_attachment = True  # Forces download
    pdf_filename = 'product_details.pdf'

# urls.py (in your app)
# urlpatterns = [
#     path('product/<int:pk>/', ProductDetailView.as_view(), name='product_detail'),
#     path('product/<int:pk>/pdf/', ProductPDFView.as_view(), name='product_pdf'),
# ]

# products/product_detail.html (example template)
# In your template directory:
# <!DOCTYPE html>
# <html>
# <head>
#     <title>{{ product.name }} PDF</title>
#     <style>
#         @page { size: A4; margin: 2cm; }
#         body { font-family: sans-serif; }
#         h1 { color: #333; }
#         .price { color: green; font-weight: bold; }
#     </style>
#     <link rel="stylesheet" type="text/css" href="{{ STATIC_URL }}css/pdf_styles.css">
# </head>
# <body>
#     <h1>{{ product.name }}</h1>
#     <p>{{ product.description }}</p>
#     <p class="price">Price: ${{ product.price }}</p>
# </body>
# </html>

# settings.py (important for static files)
# STATIC_URL = '/static/'
# STATIC_ROOT = os.path.join(BASE_DIR, 'staticfiles')

view raw JSON →