You need to enable JavaScript to run this app.
最新活动
大模型
产品
解决方案
定价
生态与合作
支持与服务
开发者
了解我们

求助:Django中使用WeasyPrint生成PDF时Bootstrap样式丢失

解决WeasyPrint生成PDF丢失Bootstrap样式的问题

我之前也踩过WeasyPrint + Bootstrap样式丢失的坑!核心问题是WeasyPrint处理静态资源的逻辑和浏览器不一样——当你用render_to_string生成HTML字符串后直接传给WeasyPrint,它没法识别模板里的相对路径静态资源引用,自然加载不到Bootstrap的CSS。下面给你几个靠谱的解决方案:

方案1:内联Bootstrap CSS(最稳妥)

把Bootstrap的CSS内容直接嵌入到HTML里,这样WeasyPrint渲染时不需要再去加载外部资源,样式肯定能生效。

步骤:

  1. 在视图里读取Bootstrap CSS文件的内容:
from django.conf import settings
import os

# 读取本地静态文件里的Bootstrap CSS
# 开发环境如果没执行collectstatic,可替换为STATICFILES_DIRS的路径
bootstrap_css_path = os.path.join(settings.STATIC_ROOT, 'css/bootstrap.min.css')

with open(bootstrap_css_path, 'r', encoding='utf-8') as f:
    bootstrap_css_content = f.read()
  1. 把CSS内容传到模板上下文:
html_string = render_to_string('index.html', {
    'data' : data,
    'total' : total_price,
    'cash' : cash_price,
    'paid' : paid,
    'hm_fees' : hm_fees,
    'invoice_number' : invoice_number,
    'total_sales' : total_sales,
    'bootstrap_css' : bootstrap_css_content  # 新增CSS内容变量
})
  1. index.html里用<style>标签嵌入CSS:
<style type="text/css">
    {{ bootstrap_css|safe }}
</style>

方案2:设置Base URL让WeasyPrint识别资源路径

如果不想内联CSS,可以给WeasyPrint的HTML对象设置base_url,让它知道去哪里找相对路径的静态资源。

修改视图里的这一行:

html = HTML(string=html_string, base_url=request.build_absolute_uri('/'))

同时确保模板里的Bootstrap引用是Django静态标签生成的相对路径:

<link rel="stylesheet" href="{% static 'css/bootstrap.min.css' %}">

base_url会告诉WeasyPrint,所有相对路径的资源都从这个URL根目录去加载,这样它就能正确获取到Bootstrap CSS了。

注意事项

  • WeasyPrint对Bootstrap的部分CSS特性支持有限(比如某些复杂的响应式布局、动画类),如果样式还是有偏差,可以尝试用Bootstrap的打印专用CSS,或者只保留你需要的CSS片段。
  • 生产环境要确保静态文件已经通过collectstatic收集到STATIC_ROOT目录下,否则WeasyPrint可能找不到资源。

内容的提问来源于stack exchange,提问作者Rutnet

火山引擎 最新活动