Django生成PDF文档显示在网页上以及解决PDF中文显示乱码的问题


Posted in Python onJuly 04, 2019

项目地址:https://github.com/PythonerKK/django-generate-pdf/tree/master

这个demo实现了通过用户输入自己的个人信息生成一份简历pdf,来阐述如何使用Django的HttpResponse生成PDF的文档。

先上效果图:

Django生成PDF文档显示在网页上以及解决PDF中文显示乱码的问题

Django生成PDF文档显示在网页上以及解决PDF中文显示乱码的问题

Django生成PDF文档显示在网页上以及解决PDF中文显示乱码的问题

安装依赖库

首先安装Django最新版2.2.2和PDF依赖包xhtml2pdf

pip install django
pip install xhtml2pdf

编写表单验证

为了简单起见,这个demo依赖数据库,只需要表单验证数据即可
pdf/forms.py

class MessageForm(forms.Form):
  '''
  表单验证
  '''
  name = forms.CharField(required=True)
  degree = forms.CharField(required=True)
  edu = forms.CharField(required=True)
  work = forms.CharField(required=True)
  tech = forms.CharField(required=True)
  phone = forms.CharField(required=True)

编写类视图

pdf/views.py
由于这里我们只需要表单视图,所以只创建了一个类视图,post用来验证表单数据是否都存在,如果存在就把表单数据渲染到PDF模板中,经过处理后返回PDF的响应response。

这里可以使用Django的通用类视图FormView构建,代码更简洁

class MessageView(View):
  def get(self, request):
    form = MessageForm(data=request.GET)
    return render(request, 'index.html', {
      'form': form
    })

  def post(self, request):
    form = MessageForm(data=request.POST)
    if form.is_valid():
      response = generate_pdf_response(context=form.cleaned_data)
      return response
    return redirect(reverse('pdf:message'))

编写生成PDF响应response

view.py这里为了方便直接把处理函数写到视图函数的文件里

def link_callback(uri):
  if uri.startswith(settings.MEDIA_URL):
    path = os.path.join(settings.MEDIA_ROOT,
              uri.replace(settings.MEDIA_URL, ""))
  elif uri.startswith(settings.STATIC_URL):
    path = os.path.join(settings.STATIC_ROOT,
              uri.replace(settings.STATIC_URL, ""))
  else:
    return uri

  # 确保本地文件存在
  if not os.path.isfile(path):
    raise Exception(
      "Media URI 必须以以下格式开头"
      f"'{settings.MEDIA_URL}' or '{settings.STATIC_URL}'")

  return path


def generate_pdf_response(context):
  response = HttpResponse(content_type="application/pdf")
  response["Content-Disposition"] = \
    f"attachment; filename='{context['name']}.pdf'"

  html = render_to_string("pdf.html", context=context)
  status = pisa.CreatePDF(html,
              dest=response,
              link_callback=link_callback)

  if status.err:
    return HttpResponse("PDF文件生成失败")
  return response

解决中文乱码问题

需要下载中文字体msyh.ttf放在static目录下的font目录,用来设置全局字体。这些文件都在github仓库里。

def font_patch():
  from reportlab.pdfbase.ttfonts import TTFont
  from reportlab.pdfbase import pdfmetrics
  from xhtml2pdf.default import DEFAULT_FONT
  pdfmetrics.registerFont(TTFont('yh', '{}/font/msyh.ttf'.format(
    settings.STATICFILES_DIRS[0])))
  DEFAULT_FONT['helvetica'] = 'yh'

把这个函数放在生成PDF响应前

Django生成PDF文档显示在网页上以及解决PDF中文显示乱码的问题

按照以上大致步骤大家就能够生成PDF文件了,可以在网页中浏览、放大、缩小,也可以下载,非常方便、简单。
大家可以直接clone一份代码试试效果

项目地址:https://github.com/PythonerKK/django-generate-pdf/tree/master

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Python 相关文章推荐
Python使用functools实现注解同步方法
Feb 06 Python
python OpenCV学习笔记之绘制直方图的方法
Feb 08 Python
Python3.6简单的操作Mysql数据库的三个实例
Oct 17 Python
使用Python控制摄像头拍照并发邮件
Apr 23 Python
Python pandas.DataFrame调整列顺序及修改index名的方法
Jun 21 Python
python日期相关操作实例小结
Jun 24 Python
使用python爬取微博数据打造一颗“心”
Jun 28 Python
使用 Python 处理3万多条数据只要几秒钟
Jan 19 Python
python GUI库图形界面开发之PyQt5美化窗体与控件(异形窗体)实例
Feb 25 Python
简述python Scrapy框架
Aug 17 Python
Opencv常见图像格式Data Type及代码实例
Nov 02 Python
sklearn中的交叉验证的实现(Cross-Validation)
Feb 22 Python
python批量修改图片尺寸,并保存指定路径的实现方法
Jul 04 #Python
python代理工具mitmproxy使用指南
Jul 04 #Python
Python批量修改图片分辨率的实例代码
Jul 04 #Python
Django 中自定义 Admin 样式与功能的实现方法
Jul 04 #Python
python3用PIL把图片转换为RGB图片的实例
Jul 04 #Python
python中比较两个列表的实例方法
Jul 04 #Python
一文秒懂python读写csv xml json文件各种骚操作
Jul 04 #Python
You might like
php使用正则表达式获取图片url的方法
2015/01/16 PHP
PHP正则之正向预查与反向预查讲解与实例
2020/04/06 PHP
Javascript 构造函数 实例分析
2008/11/26 Javascript
JQuery读取XML文件数据并显示的实现代码
2009/12/16 Javascript
javascript查找字符串中出现最多的字符和次数的小例子
2013/10/29 Javascript
js实现常用排序算法
2016/08/09 Javascript
Bootstrap复选框和单选按钮美化插件(推荐)
2016/11/23 Javascript
Javascript中的神器——Promise
2017/02/08 Javascript
jQuery插件HighCharts绘制的基本折线图效果示例【附demo源码下载】
2017/03/07 Javascript
理解nodejs的stream和pipe机制的原理和实现
2017/08/12 NodeJs
js数组实现权重概率分配
2017/09/12 Javascript
利用JS实现scroll自定义滚动效果详解
2017/10/17 Javascript
详解vue 项目白屏解决方案
2018/10/31 Javascript
Vue对象赋值视图不更新问题及解决方法
2019/06/03 Javascript
[01:10:16]DOTA2上海特级锦标赛B组资格赛#2 Fnatic VS Spirit第一局
2016/02/27 DOTA
pycharm 使用心得(九)解决No Python interpreter selected的问题
2014/06/06 Python
Python实现远程调用MetaSploit的方法
2014/08/22 Python
python处理csv数据的方法
2015/03/11 Python
python中numpy基础学习及进行数组和矢量计算
2017/02/12 Python
Python基于identicon库创建类似Github上用的头像功能
2017/09/25 Python
Python if语句知识点用法总结
2018/06/10 Python
python实现对指定字符串补足固定长度倍数截断输出的方法
2018/11/15 Python
使用Python的datetime库处理时间(RPA流程)
2019/11/24 Python
python实现ftp文件传输系统(案例分析)
2020/03/20 Python
Python作用域与名字空间原理详解
2020/03/21 Python
Python使用sqlite3模块内置数据库
2020/05/07 Python
python实现学生管理系统开发
2020/07/24 Python
用Python 爬取猫眼电影数据分析《无名之辈》
2020/07/24 Python
澳大利亚制造的羊皮靴:Original UGG Boots
2017/11/13 全球购物
小班开学寄语
2014/04/04 职场文书
求职信怎么写
2014/05/23 职场文书
运动员口号
2014/06/09 职场文书
暑期政治学习心得体会
2014/09/02 职场文书
2014领导班子四风问题对照检查材料思想汇报
2014/09/21 职场文书
见习报告怎么写
2014/10/31 职场文书
法院执行局工作总结
2015/08/11 职场文书