Java自学者论坛

 找回密码
 立即注册

手机号码,快捷登录

恭喜Java自学者论坛(https://www.javazxz.com)已经为数万Java学习者服务超过8年了!积累会员资料超过10000G+
成为本站VIP会员,下载本站10000G+会员资源,会员资料板块,购买链接:点击进入购买VIP会员

JAVA高级面试进阶训练营视频教程

Java架构师系统进阶VIP课程

分布式高可用全栈开发微服务教程Go语言视频零基础入门到精通Java架构师3期(课件+源码)
Java开发全终端实战租房项目视频教程SpringBoot2.X入门到高级使用教程大数据培训第六期全套视频教程深度学习(CNN RNN GAN)算法原理Java亿级流量电商系统视频教程
互联网架构师视频教程年薪50万Spark2.0从入门到精通年薪50万!人工智能学习路线教程年薪50万大数据入门到精通学习路线年薪50万机器学习入门到精通教程
仿小米商城类app和小程序视频教程深度学习数据分析基础到实战最新黑马javaEE2.1就业课程从 0到JVM实战高手教程MySQL入门到精通教程
查看: 618|回复: 0

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

[复制链接]
  • TA的每日心情
    奋斗
    2024-11-24 15:47
  • 签到天数: 804 天

    [LV.10]以坛为家III

    2053

    主题

    2111

    帖子

    72万

    积分

    管理员

    Rank: 9Rank: 9Rank: 9

    积分
    726782
    发表于 2021-6-7 07:24:09 | 显示全部楼层 |阅读模式

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

    这个demo实现了通过用户输入自己的个人信息生成一份简历pdf,来阐述如何使用Django的HttpResponse生成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响应前
    在这里插入图片描述

    按照以上大致步骤大家就能够生成PDF文件了,可以在网页中浏览、放大、缩小,也可以下载,非常方便、简单。
    大家可以直接clone一份代码试试效果
    项目地址:https://github.com/PythonerKK/django-generate-pdf/tree/master
    个人网页:https://liyuankun.cn

    哎...今天够累的,签到来了1...
    回复

    使用道具 举报

    您需要登录后才可以回帖 登录 | 立即注册

    本版积分规则

    QQ|手机版|小黑屋|Java自学者论坛 ( 声明:本站文章及资料整理自互联网,用于Java自学者交流学习使用,对资料版权不负任何法律责任,若有侵权请及时联系客服屏蔽删除 )

    GMT+8, 2024-12-23 07:12 , Processed in 0.061836 second(s), 29 queries .

    Powered by Discuz! X3.4

    Copyright © 2001-2021, Tencent Cloud.

    快速回复 返回顶部 返回列表