Reportlab を使用して、元は html である一部のコンテンツをフォーマットするときに問題が発生し、html が複雑すぎる場合がありました。解決策 (これは Reportlab の担当者によるものです) は、エラーが発生したときにそれをキャッチし、それを直接 PDF に出力することでした。
つまり、適切なコンテキストで問題の原因を確認できるということです。これを拡張して例外の詳細を出力することもできますが、私たちの場合、問題は html を rml に変換することだったので、入力を表示するだけで済みました。
プレッピー テンプレートには次のものが含まれます。
{{script}}
#This section contains python functions used within the rml.
#we can import any helper code we need within the template,
#to save passing in hundreds of helper functions at the top
from rml_helpers import blocks
{{endscript}}
そして、後のようなテンプレートのビット:
{{if equip.specification}}
<condPageBreak height="1in"/>
<para style="h2">Item specification</para>
{{blocks(equip.specification)}}
{{endif}}
rml_helpers.py には次のものがあります。
from xml.sax.saxutils import escape
from rlextra.radxml.html_cleaner import cleanBlocks
from rlextra.radxml.xhtml2rml import xhtml2rml
def q(stuff):
"""Quoting function which works with unicode strings.
The data from Zope is Unicode objects. We need to explicitly
convert to UTF8; then escape any ampersands. So
u"Black & Decker drill"
becomes
"Black & Decker drill"
and any special characters (Euro, curly quote etc) end up
suitable for XML. For completeness we'll accept 'None'
objects as well and output an empty string.
"""
if stuff is None:
return ''
elif isinstance(stuff,unicode):
stuff = escape(stuff.encode('utf8'))
else:
stuff = escape(str(stuff))
return stuff.replace('"','"').replace("'", ''')
def blocks(txt):
try:
txt2 = cleanBlocks(txt)
rml = xhtml2rml(txt2)
return rml
except:
return '<para style="big_warning">Could not process markup</para><para style="normal">%s</para>' % q(txt)
そのため、複雑すぎxhtml2rml
て処理できないものはすべて例外をスローし、出力で「マークアップを処理できませんでした」という大きな警告に置き換えられ、その後にエラーの原因となったマークアップがエスケープされ、リテラルとして表示されます。
次に、出力 PDF でエラー メッセージを検索し、それに応じて入力を修正することを忘れないでください。