10

我有一个 django 应用程序,它从 HTML 表单上的用户输入动态生成 PDF(使用 reportlab + pypdf),并返回带有application/pdfMIMEType 的 HTTP 响应。

我想在执行上述操作或通过电子邮件发送生成的 pdf 之间进行选择,但我不知道如何使用 EmailMessage 类的attach(filename=None, content=None, mimetype=None)方法。该文档content没有对应该是哪种对象进行太多描述。我尝试了一个文件对象和上面的application/pdfHTTP 响应。

我目前有一个解决方法,我的视图将 pdf 保存到磁盘,然后我使用该attach_file()方法将生成的文件附加到外发电子邮件。这对我来说似乎是错误的,我很确定有更好的方法。

4

4 回答 4

6

好的,我已经想通了。

中的第二个参数attach()需要一个字符串。我只是使用文件对象的read()方法来生成它正在寻找的内容:

from django.core.mail import EmailMessage

message = EmailMessage('Hello', 'Body goes here', 'from@example.com',
    ['to1@example.com', 'to2@example.com'], ['bcc@example.com'],
    headers = {'Reply-To': 'another@example.com'})
attachment = open('myfile.pdf', 'rb')
message.attach('myfile.pdf',attachment.read(),'application/pdf')

我最终改用临时文件,但概念与普通文件对象相同。

于 2010-05-07T19:16:38.900 回答
4

生成文件临时。

from django.utils import timezone    
from io import BytesIO
from reportlab.pdfgen import canvas
from reportlab.lib.pagesizes import letter

def generate_pdf(pk):
    y = 700
    buffer = BytesIO()
    p = canvas.Canvas(buffer, pagesize=letter)
    p.setFont('Helvetica', 10)
    p.drawString(220, y, "PDF generate at "+timezone.now().strftime('%Y-%b-%d'))
    p.showPage()
    p.save()
    pdf = buffer.getvalue()
    buffer.close()
    return pdf

将 PDF 附加到消息中

from django.core.mail import EmailMessage
def send(request)
    pdf = generate_pdf(pk)
    msg = EmailMessage("title", "content", to=["email@gmail.com"])
    msg.attach('my_pdf.pdf', pdf, 'application/pdf')
    msg.content_subtype = "html"
    msg.send()
于 2016-03-21T18:56:23.120 回答
0

根据您链接中的示例:

message.attach('design.png', img_data, 'image/png')

您的 pdf 内容不会与您通常写入 pdf 文件的输出相同吗?不要将 generated_pdf_data 保存到 myfile.pdf,而是将其插入 message.attach 的内容字段:

message.attach('myfile.pdf', generated_pdf_data, 'application/pdf')
于 2010-05-07T15:48:25.407 回答
0

我发现这行得通

message.attach('myfile.pdf', pdf.getvalue() , 'application/pdf')

使用时

message.attach('myfile.pdf', pdf.read() , 'application/pdf')

pdf已损坏,无法打开

于 2021-08-28T17:48:06.813 回答