我的知识记录

Python发送邮件多个附件 一次打包发送

用Python smtplib发送带多个附件的邮件,支持混合PDF/Excel/图片,自动处理中文文件名,附完整代码与目录批量打包示例。

场景痛点

周报要发Excel数据、PDF报告、PNG截图,三个文件手动拖到邮件附件区,拖完还得确认没漏。用Python把一个文件夹里所有文件自动塞进邮件,不管几个附件都不用管,跑完自动发。

用到的库

# smtplib/email都是标准库,无需安装

完整代码

# -*- coding: utf-8 -*-
import smtplib
import os
from email.mime.multipart import MIMEMultipart
from email.mime.text import MIMEText
from email.mime.base import MIMEBase
from email import encoders
from email.header import Header

SMTP_SERVER = "smtp.qq.com"
SMTP_PORT = 465
SENDER = "your_account@qq.com"
AUTH_CODE = "your_smtp_auth_code"
RECEIVER = "receiver@example.com"


def add_attachment(msg, file_path):
"""把单个文件作为附件加入邮件"""
filename = os.path.basename(file_path)
with open(file_path, "rb") as f:
part = MIMEBase("application", "octet-stream")
part.set_payload(f.read())
encoders.encode_base64(part)
part.add_header(
"Content-Disposition",
"attachment",
filename=("utf-8", "", filename)
)
msg.attach(part)


def send_multi_attach(file_list):
msg = MIMEMultipart()
msg["From"] = Header(f"数据组 <{SENDER}>", "utf-8")
msg["To"] = Header(RECEIVER, "utf-8")
msg["Subject"] = Header("本周数据包(多附件)", "utf-8")
msg.attach(MIMEText("你好,附件是本周全部数据,请查收。", "plain", "utf-8"))

# 循环把每个文件都加进去
for path in file_list:
if os.path.isfile(path):
add_attachment(msg, path)
print(f"已加入附件: {path}")
else:
print(f"文件不存在,跳过: {path}")

server = smtplib.SMTP_SSL(SMTP_SERVER, SMTP_PORT)
server.login(SENDER, AUTH_CODE)
server.sendmail(SENDER, [RECEIVER], msg.as_string())
server.quit()
print("多附件邮件发送成功")


def collect_files(folder):
"""把一个文件夹下所有文件收集成列表(不含子目录)"""
result = []
for name in os.listdir(folder):
full = os.path.join(folder, name)
if os.path.isfile(full) and not name.startswith("."):
result.append(full)
return result


if __name__ == "__main__":
# 方式一:手动指定文件列表
# files = ["/data/report.xlsx", "/data/summary.pdf", "/data/chart.png"]

# 方式二:自动收集整个文件夹
files = collect_files("/data/weekly_pack/")
send_multi_attach(files)

代码讲解

  • 把附件逻辑抽成add_attachment()函数,循环调用就行,代码干净。
  • os.listdir()遍历文件夹,过滤掉隐藏文件和子目录,只取普通文件。
  • 附件总数没有硬性限制,但总大小建议控制在20MB以内,超过就打zip包或换网盘链接。
  • 如果只想加指定类型(比如只发PDF和Excel),在collect_files里按扩展名过滤即可。

运行结果

控制台逐个打印"已加入附件: xxx",最后收件人邮箱收到一封带多个附件的邮件,每个文件名正常显示中文。

注意事项

  • 单个邮箱一般限制单封邮件总大小50MB,多附件加起来超了会发送失败。
  • 附件里不要放.exe、.bat、.cmd这类可执行文件,绝大多数邮箱直接拒收。
  • 中文文件名必须用filename=("utf-8", "", filename)这种元组写法,直接传字符串对方收到是乱码。
  • 发之前最好os.path.getsize()算一下总大小,超过30MB提前警告。

Python发送邮件多个附件 一次打包发送

标签:

更新时间:2026-09-14 21:05:28

上一篇:Python自动发送邮件 smtplib基础教程

下一篇:Python发送HTML格式邮件 排版美化教程