Question

Edit. Found the solution: it seems the pdf document has to be base64 encoded. Editing the async view as such works:

import base64
result = export_pdf(request)
encoded = base64.b64encode(result.getvalue())
email = mandrill.Mandrill(settings.MANDRILL_API_KEY)
email.messages.send_template(mandrill_template, [], {'to':[{'email':user.email}], 'subject':subject, 'text':message, attachments':[{'type':'application/pdf', 'name':'pdf file', 'content':encoded}] })

end of edit

I have a problem sending a pdf document created with xhtml2pdf/pisa as a attachement in Mandrill. The application work as follows: a content_view calls an async_view which

  1. generates the pdf (by calling an export_pdf function) and
  2. sends the email with attachment.

The pdf document seems valid (if I modify the async_view to HttpResponse the pdf instead of sending it, I see a valid pdf document). But sending it to Mandrill returns an encoding error:

UnicodeDecodeError: 'utf8' codec can't decode byte 0x93 in position 11: invalid start byte.

I tried to solve it as mentionned here (Python: Sanitize a string for unicode?). In this case, no error is raised anymore, but the pdf I get as email attachement is considered as 'text/plain' and not readable. Thank you for your help!

async_view

pdf_doc = export_pdf(request).getvalue() # .decode("windows-1252").encode("utf-8", 'ignore') would not raise an error but would be considered as plain text
email = mandrill.Mandrill(settings.MANDRILL_API_KEY)
email.messages.send_template(mandrill_template, [], {'to':[{'email':user.email}], 'subject':subject, 'text':message, attachments':[{'type':'application/pdf', 'name':'pdf file', 'content':pdf_doc}] })

# return HttpResponse(pdf_doc,  mimetype='application/pdf') would return a well formatted pdf

export_pdf function

def export_pdf(request):

    html  = render_to_string('pdf.html', { 'pagesize' : 'A4', }, context_instance=RequestContext(request,{
                'text': text,
            },))
    result = cStringIO.StringIO()       
    pdf = pisa.pisaDocument(StringIO.StringIO(html), dest=result, encoding='UTF-8')
    if not pdf.err:
        return result
    else:
        return None

the interresting part of the traceback is

(...)
File "/home/raphael/Applications/Virtualenvs/apps/local/lib/python2.7/site-packages/mandrill.py", line 1476, in send_template
    return self.master.call('messages/send-template', _params)
File "/home/raphael/Applications/Virtualenvs/apps/local/lib/python2.7/site-packages/mandrill.py", line 137, in call
    params = json.dumps(params)
File "/home/raphael/Applications/Virtualenvs/apps/local/lib/python2.7/site-packages/simplejson/__init__.py", line 354, in dumps
    return _default_encoder.encode(obj)
File "/home/raphael/Applications/Virtualenvs/apps/local/lib/python2.7/site-packages/simplejson/encoder.py", line 262, in encode
    chunks = self.iterencode(o, _one_shot=True)
File "/home/raphael/Applications/Virtualenvs/apps/local/lib/python2.7/site-packages/simplejson/encoder.py", line 340, in iterencode
    return _iterencode(o, 0)
UnicodeDecodeError: 'utf8' codec can't decode byte 0x93 in position 11: invalid start byte
Was it helpful?

Solution

Found the solution: it seems the pdf document has to be base64 encoded. Editing the async view as such works:

import base64
result = export_pdf(request)
encoded = base64.b64encode(result.getvalue())
email = mandrill.Mandrill(settings.MANDRILL_API_KEY)
email.messages.send_template(mandrill_template, [], {'to':[{'email':user.email}], 'subject':subject, 'text':message, attachments':[{'type':'application/pdf', 'name':'pdf file', 'content':encoded}] })
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top