将 xhtml2pdf 的相对 url 路径转换为绝对 url 路径
Converting relative url path to absolute url for xhtml2pdf
我在这方面非常缺乏经验,所以我很难理解 documentation provided 和 xhtml2pdf
,因为它在细节上非常模糊。请告诉我我做错了什么。
根据文档将相对 url 路径转换为绝对路径我需要使用提供的函数:
def link_callback(uri, rel):
"""
Convert HTML URIs to absolute system paths so xhtml2pdf can access those
resources
"""
# use short variable names
sUrl = settings.STATIC_URL # Typically /static/
sRoot = settings.STATIC_ROOT # Typically /home/userX/project_static/
mUrl = settings.MEDIA_URL # Typically /static/media/
mRoot = settings.MEDIA_ROOT # Typically /home/userX/project_static/media/
# convert URIs to absolute system paths
if uri.startswith(mUrl):
path = os.path.join(mRoot, uri.replace(mUrl, ""))
elif uri.startswith(sUrl):
path = os.path.join(sRoot, uri.replace(sUrl, ""))
else:
return uri # handle absolute uri (ie: http://some.tld/foo.png)
# make sure that file exists
if not os.path.isfile(path):
raise Exception(
'media URI must start with %s or %s' % (sUrl, mUrl)
)
return path
我向我的 views.py
添加了完全相同的函数并使用此函数生成 pdf(也在 views.py
中,几乎直接采用了文档形式):
def PGP_result(request):
data = request.session['form_data']
lietuvosPgp = data['LtPGP']
valstybe = data['pVal']
kastai = data['iKastai']
rezultatas = data['result']
today = timezone.now()
params = {
'LtPgp': lietuvosPgp,
'Valstybe': valstybe,
'Kastai': kastai,
'Rezultatas': rezultatas,
'today': today,
}
template_path = 'PGP_results_pdf.html'
response = HttpResponse(content_type='application/pdf')
response['Content-Disposition'] = 'attachment; filename="test.pdf"'
template = get_template(template_path)
html = template.render(params)
pisaStatus = pisa.CreatePDF(
html, dest=response, link_callback=link_callback
)
if pisaStatus.err:
return HttpResponse('Ups kažkas nepavyko <pre>' + html + '</pre>')
return response
Pdf 已生成,但未使用驻留在 static/fonts
文件夹中的字体文件。我不知道如何正确编写相对 url 路径,以便将其转换为绝对路径。我想解决方案应该很简单,但我缺乏经验使我无法找到它(我厌倦了各种写法,但 none 其中有效)。
我的(当前)模板代码(不知道如何修复 src: url(sUrl/fonts/Arial.ttf)
部分):
<!doctype html>
<html>
<head>
<meta charset="utf-8">
<title>Test</title>
<style type="text/css">
@font-face {
font-family: "Arial"; src: url(sUrl/fonts/Arial.ttf);
}
.container {
font-family: "Arial"
}
</style>
</head>
<body>
<div class="container">
<div class="card">
<div class="card-header">
<h3>Skaičiuota - {{ today | date:"d/m/Y" }}</h3>
</div>
<div class="list-group">
<p>{{ LtPgp }}</p>
<p>{{ Valstybe }}</p>
<p>{{ Kastai }}</p>
<p>{{ Rezultatas }}</p>
</div>
</div>
</div>
</body>
</html>
阅读了一堆或多或少类似的问题后,我无意中发现了建议先使用 运行 py manage.py collectstatic
命令的评论。阅读本文并分析 `link_callback 函数后,我找到了解决方案:
在模板中应该是:font-family: "Arial"; src: "static/fonts/Arial.ttf";
在我的结论中 link_callback
函数检查 link 的第一部分,如果它发现 link 以 static
开头,则将其替换为 [=14] 的目录=](绝对路径)。由于我在使用 Debug=True
的开发服务器上工作,所以我不需要 collectstatic
处理其他所有内容,因此虽然一切正常,但 link_callback
函数指向不存在的(尚未)目录。在收集了所有的静态数据并修复了源代码后 link 我开始工作了。
P.S。我不是专业的,也没有编程背景,所以如果我的假设是错误的,请修正(我真的很想学习和了解更多)。但即使假设错误,代码现在也能正常工作。
我在这方面非常缺乏经验,所以我很难理解 documentation provided 和 xhtml2pdf
,因为它在细节上非常模糊。请告诉我我做错了什么。
根据文档将相对 url 路径转换为绝对路径我需要使用提供的函数:
def link_callback(uri, rel):
"""
Convert HTML URIs to absolute system paths so xhtml2pdf can access those
resources
"""
# use short variable names
sUrl = settings.STATIC_URL # Typically /static/
sRoot = settings.STATIC_ROOT # Typically /home/userX/project_static/
mUrl = settings.MEDIA_URL # Typically /static/media/
mRoot = settings.MEDIA_ROOT # Typically /home/userX/project_static/media/
# convert URIs to absolute system paths
if uri.startswith(mUrl):
path = os.path.join(mRoot, uri.replace(mUrl, ""))
elif uri.startswith(sUrl):
path = os.path.join(sRoot, uri.replace(sUrl, ""))
else:
return uri # handle absolute uri (ie: http://some.tld/foo.png)
# make sure that file exists
if not os.path.isfile(path):
raise Exception(
'media URI must start with %s or %s' % (sUrl, mUrl)
)
return path
我向我的 views.py
添加了完全相同的函数并使用此函数生成 pdf(也在 views.py
中,几乎直接采用了文档形式):
def PGP_result(request):
data = request.session['form_data']
lietuvosPgp = data['LtPGP']
valstybe = data['pVal']
kastai = data['iKastai']
rezultatas = data['result']
today = timezone.now()
params = {
'LtPgp': lietuvosPgp,
'Valstybe': valstybe,
'Kastai': kastai,
'Rezultatas': rezultatas,
'today': today,
}
template_path = 'PGP_results_pdf.html'
response = HttpResponse(content_type='application/pdf')
response['Content-Disposition'] = 'attachment; filename="test.pdf"'
template = get_template(template_path)
html = template.render(params)
pisaStatus = pisa.CreatePDF(
html, dest=response, link_callback=link_callback
)
if pisaStatus.err:
return HttpResponse('Ups kažkas nepavyko <pre>' + html + '</pre>')
return response
Pdf 已生成,但未使用驻留在 static/fonts
文件夹中的字体文件。我不知道如何正确编写相对 url 路径,以便将其转换为绝对路径。我想解决方案应该很简单,但我缺乏经验使我无法找到它(我厌倦了各种写法,但 none 其中有效)。
我的(当前)模板代码(不知道如何修复 src: url(sUrl/fonts/Arial.ttf)
部分):
<!doctype html>
<html>
<head>
<meta charset="utf-8">
<title>Test</title>
<style type="text/css">
@font-face {
font-family: "Arial"; src: url(sUrl/fonts/Arial.ttf);
}
.container {
font-family: "Arial"
}
</style>
</head>
<body>
<div class="container">
<div class="card">
<div class="card-header">
<h3>Skaičiuota - {{ today | date:"d/m/Y" }}</h3>
</div>
<div class="list-group">
<p>{{ LtPgp }}</p>
<p>{{ Valstybe }}</p>
<p>{{ Kastai }}</p>
<p>{{ Rezultatas }}</p>
</div>
</div>
</div>
</body>
</html>
阅读了一堆或多或少类似的问题后,我无意中发现了建议先使用 运行 py manage.py collectstatic
命令的评论。阅读本文并分析 `link_callback 函数后,我找到了解决方案:
在模板中应该是:font-family: "Arial"; src: "static/fonts/Arial.ttf";
在我的结论中 link_callback
函数检查 link 的第一部分,如果它发现 link 以 static
开头,则将其替换为 [=14] 的目录=](绝对路径)。由于我在使用 Debug=True
的开发服务器上工作,所以我不需要 collectstatic
处理其他所有内容,因此虽然一切正常,但 link_callback
函数指向不存在的(尚未)目录。在收集了所有的静态数据并修复了源代码后 link 我开始工作了。
P.S。我不是专业的,也没有编程背景,所以如果我的假设是错误的,请修正(我真的很想学习和了解更多)。但即使假设错误,代码现在也能正常工作。