首页 > 解决方案 > 为什么我无法使用 Python3 发送带有 excel 附件的电子邮件

问题描述

我认为问题出在参数中server=... ,我应该在这里放什么?

import smtplib
import os
from email.mime.multipart import MIMEMultipart
from email.mime.base import MIMEBase
from email.mime.text import MIMEText
from email.utils import COMMASPACE, formatdate
from email import encoders


def send_mail(send_from, send_to, subject, text, files=[], server=r'\\myserver\User\name\PythonProject\'):
  assert type(send_to)==['sendto@.com']
  assert type(files)==['File Name.xlsx']
  msg = MIMEMultipart()
  msg['From'] = "sendfrom@.com"
  msg['To'] = COMMASPACE.join(send_to)
  msg['Date'] = formatdate(localtime=True)
  msg['Subject'] = subject
  msg.attach( MIMEText(text) )
  for f in files:
    part = MIMEBase('application', "octet-stream")
    part.set_payload( open(files,"rb").read() )
    encoders.encode_base64(part)
    part.add_header('Content-Disposition', 'attachment; filename="%s"' % os.path.basename(f))
    msg.attach(part)
  smtp = smtplib.SMTP('1.1.1.1: 25')
  smtp.sendmail(send_from, send_to, msg.as_string())
  smtp.close()

标签: pythonpython-3.xsmtplib

解决方案


这段代码有很多问题。

  • server函数签名中 的默认值
    • 字符串以 结尾\',它转义结束引号:删除它或转义它(“r”前缀转义字符串的反斜杠,但终端反斜杠被解释为转义结束引号,因此在字符串之外)
    • server未在函数中使用
  • 使用可变的默认值通常files=[]是个坏主意。files=None在尝试迭代之前更好地使用和检查代码中的值
  • 这些assert陈述不起作用。
  • part.set_payload( open(files,"rb").read() )正在尝试打开文件列表,它只需要在循环中打开当前文件:open(f, ...)

这是代码的“固定”版本

def send_mail(
    send_from,
    send_to,
    subject,
    text,
    files=None,
    server=r"\\myserver\User\name\PythonProject\\",
):
    assert isinstance(send_to, list)
    assert isinstance(files, list)
    msg = MIMEMultipart()
    msg["From"] = "sendfrom@.com"
    msg["To"] = COMMASPACE.join(send_to)
    msg["Date"] = formatdate(localtime=True)
    msg["Subject"] = subject
    msg.attach(MIMEText(text))
    if files is not None:
        for f in files:
            part = MIMEBase("application", "octet-stream")
            part.set_payload(open(f, "rb").read())
            encoders.encode_base64(part)
            part.add_header(
                "Content-Disposition", 'attachment; filename="%s"' % os.path.basename(f)
            )   
        msg.attach(part)
    smtp = smtplib.SMTP('1.1.1.1:25')
    smtp.sendmail(send_from, send_to, msg.as_string())
    smtp.close()

推荐阅读