使用 Boto3 操作 Amazon SES v2:从邮件附件到订阅邮件 Newsletter 的完整实战指南

发布时间:2026/9/28 3:52:14

使用 Boto3 操作 Amazon SES v2:从邮件附件到订阅邮件 Newsletter 的完整实战指南 示例工程教程后端【免费下载链接】aws-doc-sdk-examplesWelcome to the AWS Code Examples Repository. This repo contains code examples used in the AWS documentation, AWS SDK Developer Guides, and more. For more information, see the Readme.md file below.项目地址https://gitcode.com/gh_mirrors/aw/aws-doc-sdk-examples点击查看免费下载本篇技术指南以 AWS 官方代码示例仓库中 python/example_code/sesv2/README.md 为骨架系统讲解如何通过 AWS SDK for PythonBoto3调用 Amazon Simple Email Service v2 APISES v2。仓库中的代码示例覆盖三类典型场景入门级的身份列表查询Hello SESv2、带附件的单发与批量邮件发送、以及面向订阅用户的 Coupon Newsletter 工作流。读完本文你将掌握 SESv2 的核心 API 调用方式、附件与内联图片的实现细节、模板化批量群发与联系人列表的管理流程并能在本地直接运行、测试这些示例。概览SES v2 API 与 Boto3Amazon SES v2 API 是 Amazon Simple Email Service 的第二代 API定位为一种可靠、可扩展且经济高效的邮件发送服务。与第一代 APIses相比v2 在 API 组织方式、联系人管理Contact Lists以及批量发送能力上进行了重构。本文涉及的全部示例均位于仓库的python/example_code/sesv2目录整体结构如下attachments_scenario/邮件附件场景包含封装层 sesv2_wrapper.py、入口脚本 scenario_sesv2_email_attachments.py、入门示例 sesv2_hello.py以及集成测试attachments_scenario/test/test_sesv2_email_attachments.pynewsletter_scenario/Newsletter 订阅工作流入口为 newsletter.py配套测试为newsletter_scenario/test/newsletter_test.pyrequirements.txt依赖清单。运行前置条件Prerequisites在运行任何示例之前需要满足以下条件拥有一个 AWS 账户并按 python/README.md 中描述的方式配置好默认凭证credentials与默认 AWS Region安装 Python 3.6 或更高版本在虚拟环境中安装示例所需的依赖包python -m pip install -r requirements.txtrequirements.txt 内容如下boto31.35.0 botocore1.35.0 pytest7.2.1其中pytest用于运行示例目录下的测试用例。注意运行这些代码可能产生 AWS 费用无论直接运行还是运行测试都可能对您的 AWS 账户计费。官方建议遵循最小权限原则least privilege仅授予执行任务所需的最低 IAM 权限。关于 SES Sandbox 的说明如果账户处于 SES 沙箱Sandbox模式发件地址与收件地址都必须是经过验证的邮箱身份。这一点在两个场景的源码中都有体现邮件附件场景的启动脚本会在收集地址时提示“Both sender and recipient addresses must be verified if your account is in the SES sandbox”见 scenario_sesv2_email_attachments.pyNewsletter 工作流也要求用户输入已验证邮箱作为发件身份。若已脱离沙箱生产模式则只需验证发件地址。快速入门Hello Amazon SES v2 API入门示例演示了创建 SESv2 客户端并列出账户中邮件身份Email Identities的最小完整流程核心函数为 sesv2_hello.py 中的hello_sesv2def hello_sesv2(sesv2_client): print(Hello, Amazon SESv2. Lets list up to 5 email identities:\n) try: response sesv2_client.list_email_identities(PageSize5) identities response[EmailIdentities] if not identities: print(No email identities found. Use CreateEmailIdentity to add one.) else: for identity in identities: print( f Identity: {identity[IdentityName]} f Type: {identity[IdentityType]} f Status: {identity[VerificationStatus]} f Sending: {Enabled if identity[SendingEnabled] else Disabled} ) except ClientError as err: logger.error(...) raise要点boto3.client(sesv2)使用共享凭证文件~/.aws/credentials与配置文件中的默认设置创建客户端list_email_identities(PageSize5)只取前 5 个身份返回项包含IdentityName、IdentityType、VerificationStatus、SendingEnabled等字段异常统一通过ClientError捕获并按err.response[Error][Code]与Message记录日志后重新抛出。运行方式python attachments_scenario/sesv2_hello.py单操作示例Single actions下表汇总了 README 中列出的每个独立 API 操作及其在源码中的实现位置方便按需查阅API 操作源码位置说明CreateContactnewsletter.py在联系人列表中创建订阅者CreateContactListnewsletter.py创建联系人列表Newsletter 订阅者池CreateEmailIdentitysesv2_wrapper.py发起邮箱或域名身份验证流程CreateEmailTemplatesesv2_wrapper.py创建邮件模板支持{{placeholder}}变量DeleteContactListnewsletter.py删除联系人列表DeleteEmailIdentitysesv2_wrapper.py删除邮件身份DeleteEmailTemplatesesv2_wrapper.py删除邮件模板GetEmailIdentitysesv2_wrapper.py查询身份信息与验证状态ListContactsnewsletter.py列出联系人列表中的全部订阅者SendBulkEmailsesv2_wrapper.py单次 API 调用向多个收件人发送模板化邮件SendEmailsesv2_wrapper.py发送单封邮件Simple 或 Template 内容类型封装类 SESv2Wrapper 的工程价值除 Newsletter 场景直接使用boto3.client(sesv2)外附件场景将全部 API 调用收敛进 SESv2Wrapper 类class SESv2Wrapper: def __init__(self, sesv2_client: Any) - None: self.sesv2_client sesv2_client classmethod def from_client(cls) - SESv2Wrapper: sesv2_client boto3.client(sesv2) return cls(sesv2_client)该封装层带来两点收益一是通过from_client()类方法统一创建客户端便于测试时注入 mock 客户端二是每个方法内部都对ClientError的典型错误码做了分类处理。例如create_email_identity捕获LimitExceededException并提示“已达身份数量上限请复用已验证身份”sesv2_wrapper.pyget_email_identity对NotFoundException仅记录日志后抛出由上层决定是否新建身份sesv2_wrapper.py。场景一Email Attachments Scenario邮件附件发送该场景是 SESv2 新特性附件原生支持的完整演示SES 自动完成 MIME 组装开发者无需手工构造 raw MIME 消息。启动脚本 scenario_sesv2_email_attachments.py 按照“Setup → 三步骤发送 → Cleanup”的流程运行python attachments_scenario/scenario_sesv2_email_attachments.pySetup身份校验、模板创建_setup()首先交互式收集发件与收件地址逗号分隔多个收件人随后调用get_email_identity检查发件身份是否已验证若返回NotFoundException则调用create_email_identity新建身份并提示用户去邮箱点击验证链接后继续scenario_sesv2_email_attachments.py。接着创建批量发送所需模板AttachmentDemoTemplateself.sesv2_wrapper.create_email_template( template_nameself.TEMPLATE_NAME, subjectBulk Email with Attachment for {{name}}, html_bodyh1Hello {{name}}/h1pPlease find the attached document./p, text_bodyHello {{name}}, Please find the attached document., )若模板已存在代码捕获AlreadyExistsException后直接复用scenario_sesv2_email_attachments.py。Step 1发送带文件附件的简单邮件单个附件的字典结构如下源码见 scenario_sesv2_email_attachments.pyattachment { RawContent: sample_content, # bytes文件原始内容 FileName: sample-report.txt, # 附件文件名 ContentType: text/plain, # MIME 类型 ContentDisposition: ATTACHMENT, # 附件语义下载 ContentDescription: Sample report text file, ContentTransferEncoding: BASE64, # 传输编码 }随后通过send_email发送message_id self.sesv2_wrapper.send_email( from_addressself.sender_email, to_addressesself.recipient_emails, subjectSESv2 Attachment Demo - Simple Email with Attachment, html_bodyh1Attachment Demo/h1pPlease see the attached breport document/b./p, text_bodyPlease see the attached report document., attachments[attachment], )封装层 send_email 的调用细节值得注意内容类型为Content{Simple: ...}Body同时提供Html与Text两种渲染附件通过simple_message[Attachments] attachments附加。代码注释明确提醒sesv2_wrapper.py使用 SDK 时 base64 编码由 SDK 自动处理直接调用 API 的调用方需要自行编码。若邮件被拒绝MessageRejected错误处理会提示检查附件文件类型是否受支持、总消息大小是否小于 40 MBsesv2_wrapper.py。Step 2发送带内联图片的简单邮件内联图片与附件的区别在于ContentDisposition设为INLINE并额外提供ContentId供 HTML 通过cid:引用scenario_sesv2_email_attachments.pyattachment { RawContent: sample_image, # 最小 1x1 红色 PNG 的字节流 FileName: logo.png, ContentType: image/png, ContentDisposition: INLINE, ContentId: logo123, ContentDescription: Company logo, ContentTransferEncoding: BASE64, } html_body ( htmlbodyh1Inline Image Demo/h1 pHere is our logo:/p img srccid:logo123 altCompany Logo /body/html )关键机制ContentId的值logo123与 HTML 中img srccid:logo123一一对应SES 在组装 MIME 时会把该内联资源嵌入邮件使图片直接渲染在邮件正文中而非作为可下载附件出现。场景中直接以字节字面量构造了一个合法的最小 PNG 文件含 PNG signature、IHDR、IDAT、IEND 等 chunk可在无本地文件的情况下完成演示。Step 3批量发送模板化邮件SendBulkEmailsend_bulk_email通过一次 API 调用向多个收件人发送同一模板的邮件并支持逐收件人个性化模板数据同时所有收件人共享同一份附件scenario_sesv2_email_attachments.pybulk_entries [] for i, email in enumerate(self.recipient_emails): name names[i] if i len(names) else fRecipient{i 1} bulk_entries.append({ Destination: {ToAddresses: [email]}, ReplacementEmailContent: { ReplacementTemplate: { ReplacementTemplateData: json.dumps({name: name}) } }, }) results self.sesv2_wrapper.send_bulk_email( from_addressself.sender_email, template_nameself.TEMPLATE_NAME, default_template_data{name: Valued Customer}, bulk_entriesbulk_entries, attachments[attachment], )封装层实现sesv2_wrapper.py将默认模板内容放在DefaultContent{Template: ...}附件同样挂在该默认内容下返回的BulkEmailEntryResults列表逐条包含Status、MessageId、Error字段脚本会逐收件人打印发送结果便于排查个别失败项。Cleanup资源清理_cleanup()先删除模板AttachmentDemoTemplate对NotFoundException容错再询问用户是否删除本次新建的邮件身份仅当identity_was_created为 True 时才询问预先存在的身份不会被误删见 scenario_sesv2_email_attachments.py。场景二Newsletter 订阅邮件工作流Newsletter 场景是一个完整的“订阅 → 欢迎邮件 → 周期性优惠券邮件 → 监控 → 清理”工作流被收纳在 newsletter.py 中同时参考 scenarios/features/sesv2_weekly_mailer/README.md 的用法说明。运行命令python newsletter_scenario/newsletter.py如需运行 Newsletter 示例需将scenarios/features/sesv2_weekly_mailer/resources目录中的资源文件welcome.html、coupon-newsletter.html、coupon-newsletter.txt、sample_coupons.json等复制到当前newsletter_scenario文件夹。代码中的load_file_content辅助函数在文件缺失时返回Missing file_path占位文本而非直接崩溃newsletter.py。工作流核心类SESv2Workflow的main()编排顺序为prepare_application→gather_subscriber_email_addresses→send_coupon_newsletter→monitor_and_review→clean_upnewsletter.py。1. 应用准备prepare_application依次创建三样资源并对AlreadyExistsException幂等处理Email Identitycreate_email_identity(EmailIdentityverified_email)接收用户输入的已验证发件邮箱newsletter.pyContact Listcreate_contact_list(ContactListNameweekly-coupons-newsletter)即订阅者池newsletter.pyEmail Template模板名weekly-couponsTemplateContent同时提供Subject、Html、TextHTML 与文本正文分别从coupon-newsletter.html/coupon-newsletter.txt读取newsletter.py。2. 收集订阅者并发送欢迎邮件gather_subscriber_email_addresses该步骤巧妙利用email subaddress 后缀别名技术用同一个基础邮箱生成 3 个变体作为测试订阅者从而最小化所需邮箱数量def get_subaddress_variants(base_email, num_variants): user_part, domain_part base_email.split() return [f{user_part}ses-weekly-newsletter-{i}{domain_part} for i in range(1, num_variants 1)]对每个变体执行create_contact加入联系人列表随后用Content{Simple: ...}发送欢迎邮件newsletter.py。沙箱模式下发送频率限制为每秒 1 封因此代码在每封邮件后sleep(1.1)并注明生产环境应移除newsletter.py。3. 发送优惠券 Newslettersend_coupon_newsletter通过list_contacts(ContactListName...)拉取全部订阅者若列表不存在则打印提示并返回newsletter.py从sample_coupons.json读取优惠券数据作为模板数据对每个联系人以模板内容类型发送邮件并带上退订管理选项newsletter.pyself.ses_client.send_email( FromEmailAddressself.verified_email, Destination{ToAddresses: [email_address]}, Content{ Template: { TemplateName: TEMPLATE_NAME, TemplateData: coupon_items, } }, ListManagementOptions{ContactListName: CONTACT_LIST_NAME}, )ListManagementOptions会为邮件自动追加退订链接与头部符合批量邮件bulk email最佳实践。同样受沙箱限速约束逐封sleep(1.1)。4. 监控与回顾monitor_and_review工作流指导用户前往 AWS 控制台的 SES 主页SES Homepage查看账户级仪表盘与各项指标用于评估 Newsletter 活动的送达表现。同时代码给出提醒由于该场景刻意使用 subaddress 变体来演示 Contact List 能力邮件服务商很可能将这些邮件标记为垃圾邮件检查时应同时查看垃圾邮件文件夹见 scenarios/features/sesv2_weekly_mailer/README.md。5. 清理clean_up依次删除联系人列表、邮件模板并询问用户是否删除发件身份输入y才删除。所有删除操作均对NotFoundException容错newsletter.py。运行测试Tests两个场景均配有测试目录运行测试同样可能产生 AWS 费用。完整的测试运行说明见 python/README.md。附件场景集成测试test_sesv2_email_attachments.py 通过pytest.mark.integ标记调用真实 SESv2 API需要设置环境变量SENDER_EMAIL已验证的发件邮箱与可选的RECIPIENT_EMAIL未设置时默认发给发件人自己。测试覆盖get_email_identity返回身份信息、模板创建与删除、带附件发送断言返回非空MessageId、内联图片发送、批量模板化发送断言BulkEmailEntryResults[0][Status] SUCCESS以及 Hello 示例输出。若未设置SENDER_EMAIL对应用例自动pytest.skipNewsletter 工作流测试newsletter_test.py 采用unittest.mock.patch注入 mock 客户端属于纯单元测试。它覆盖四个测试类prepare_application的成功路径与AlreadyExistsException/NotFoundException/LimitExceededException分支、gather_subscriber_email_addresses的 subaddress 变体生成与发送失败分支、send_coupon_newsletter的联系人遍历与MessageRejected容错、clean_up的三种删除路径与用户输入分支并断言各场景的控制台输出完全符合预期字符串。常见错误码与处理策略综合两个场景的源码SESv2 操作中最常见的异常码及处理方式如下错误码触发场景源码处理方式NotFoundException查询/删除不存在的身份、模板、联系人列表记录日志后继续或在删除时视为“已清理”AlreadyExistsException重复创建身份、模板、联系人、联系人列表打印提示后跳过实现幂等LimitExceededException身份或模板数量超上限提示先删除未用资源或复用已有身份然后重新抛出MessageRejected邮件被拒绝附件类型不支持、消息超 40 MB 等输出具体拒绝原因随后重新抛出所有ClientError均通过err.response[Error][Code]与err.response[Error][Message]提取诊断信息这套模式可直接迁移到您自己的生产代码中。附加资源与延伸阅读如需了解本仓库中 SESv2 Newsletter 场景在 Java、Rust、.NET 等其他语言的实现可参阅 scenarios/features/sesv2_weekly_mailer/README.md更多 SESv2 API 调用语义可查阅 Boto3 文档中sesv2服务的客户端参考如send_email、send_bulk_email、create_contact_list的请求/响应结构本文所引源码均为 Amazon.com, Inc. 或其关联方版权所有基于 Apache-2.0 许可证分发。Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.SPDX-License-Identifier: Apache-2.0赞分享示例工程教程后端【免费下载链接】aws-doc-sdk-examplesWelcome to the AWS Code Examples Repository. This repo contains code examples used in the AWS documentation, AWS SDK Developer Guides, and more. For more information, see the Readme.md file below.项目地址https://gitcode.com/gh_mirrors/aw/aws-doc-sdk-examples点击查看免费下载相关推荐使用boto3管理Amazon SES邮件模板的完整指南使用boto3管理Amazon SES邮件模板的完整指南 概述 Amazon Simple Email Service SES 是一项强大的云邮件发送服务而b后端云原生AWS SDK for Java 2.x 的 Amazon SES 邮件开发指南从单接口调用到 Newsletter 完整工作流AWS SDK for Java 2.x 的 Amazon SES 邮件开发指南从单接口调用到 Newsletter 完整工作流 本文基于 javav2/ex示例工程教程后端使用 Boto3AWS SDK for Python操作 Amazon SES身份验证、模板邮件、IP 过滤器与收件规则完整实战指南使用 Boto3AWS SDK for Python操作 Amazon SES身份验证、模板邮件、IP 过滤器与收件规则完整实战指南 Amazon Sim后端云原生上一篇Grasscutter 服务器完整部署指南功能特性、Cultivation 一键启动与 Gradle 编译法语 README 深度解读下一篇Data Formulator 多语言与 Agent 语言注入开发规范从 Accept-Language 到 LLM Prompt 的完整链路创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
延伸阅读

更多相关文章

2026/9/28 3:52:14

市面上专业的IP驱动产业新场景新工具有哪些

引言行业报告显示,2024年国内IP数字化产业落地增速超过42%,越来越多实体门店、康养机构、个人创作者不再满足于单纯的IP内容曝光,更希望把IP积累的信任资产转化为稳定的经营收益。当前市面上的IP驱动产业新场景工具赛道快速分化,不…

2026/9/28 3:47:13

STM32F407 DCMI接口接高速并口ADC的完整攻略

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/9/28 5:47:20

Rust+Slint 跨平台 GUI 入门:用 TaoToken 统一 Key 打通 AI 辅助配置

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/9/28 5:47:20

minisip-0.7.0源码实战:SIP协议解析与C++编译排错

简介:minisip-0.7.0.tar.gz 是一份基于 C 实现的开源 SIP 用户代理完整源码,面向 VoIP 开发者、网络协议学习者及需要二次开发 SIP 客户端的技术人员。资源紧密围绕 SIP 协议的核心机制,涵盖注册、呼叫、会话管理、摘要认证与 TLS 加密等关键…

2026/9/28 5:47:20

基于OpenCV与YOLO的车辆多维特征识别系统实战

简介:Python结合OpenCV和YOLOv的车辆多维特征识别系统,提供完整源代码与预训练权重,面向智能交通、安防监控等领域开发者。系统可识别车色、车品牌、车标及车型,通过OpenCV预处理图像、YOLOv模型完成目标检测与特征提取&#xff0…

2026/9/28 5:47:20

Linux性能监控利器nmon:从实时监控到故障定位实战指南

1. 项目概述与工具定位1.1 为什么还需要一款"老牌"监控工具做过Linux运维的朋友应该都有这种感觉:系统监控工具多得眼花缭乱,从系统自带的top、vmstat、iostat,到后来崛起的PrometheusGrafana组合,再到各种Agent采集方案…

2026/9/28 3:03:23

东莞市品牌网站建设报价常见报错与解决

东莞品牌网站建设报价单背后:一份保姆级建站教程避坑实录 网站做好了没人访问,这大概是很多老板最头疼的事。花了大几万做的品牌站,上线后流量惨淡,比路边摊还冷清。别急着骂外包公司,很多“东莞品牌网站建设报价”里藏着不少猫腻,比如用模板站冒充定制…

2026/9/27 0:00:45

如何划分训练/验证集:Spirula Studio五种eval_mode策略详解

如何划分训练/验证集:Spirula Studio五种eval_mode策略详解 【免费下载链接】spirula-studio Cross-vendor 3D Gaussian Splatting trainer - video to splat to mesh, Vulkan or CUDA. 项目地址: https://gitcode.com/GitHub_Trending/sp/spirula-studio Sp…

2026/9/27 0:00:45

SEO怎么推广速查手册新手避坑实战指南

SEO怎么推广速查手册新手避坑实战指南 模板网站太丑不够用?别急着加滤镜,那是治标不治本。很多老板盯着后台流量掉得眼红,却还在纠结首页Banner的圆角是不是3像素。这就像穿着西装去挖土,姿势不对,努力白费。我整理这份 速查手册…

2026/9/28 0:02:03

广州外贸网站建设推广:从零搭建全流程拆解与真实报价避坑

广州外贸网站建设推广:从零搭建全流程拆解与真实报价避坑 改个需求建站公司拖一周,后台改个文案还得再交一笔“技术维护费”。这种憋屈事儿,做外贸的朋友太熟悉了。很多老板在找广州外贸网站建设推广服务商时,光盯着首页好不好看,却忽略了从零搭建一个能…

2026/9/28 0:02:04

搞懂百度竞价推广价格,网站性能优化别掉链子

搞懂百度竞价推广价格,网站性能优化别掉链子 网站突然打不开,浏览器弹出红色警告“此网站存在安全风险”,后台一看全是乱码代码和奇怪的跳转链接。这种网站被黑挂马的绝望感,很多刚转行做网站的朋友都经历过,尤其是那些为了省几百块钱服务器费用的新手。…

2026/9/25 20:55:38

USB Type-C PCB布局分区设计:电源、高速信号与PD协议全攻略

做硬件这行,Type-C接口算是典型的“看着简单,做起来全坑”的东西。光引脚就24个,高低速信号、电源、控制线全部塞在一个小小的连接器里,如果PCB布局不做规划,打样回来基本就是“插上没反应”、“高速掉线”、“静电一打…

2026/9/26 19:58:38

系统编程学习原型如何补齐稳定性边界

系统编程学习原型如何补齐稳定性边界预算有限时&#xff0c;我先优化明显多余的复制&#xff0c;而不是猜测性地换容器。用借用传递只读数据通常就能减少分配&#xff1a; fn parse(line: &str) -> Result<Item, Error> { /* ... */ }用基准确认热点确实在分配&am…

2026/9/28 1:59:25

雨花区哪家财务公司代理记账比较好?

在雨花区&#xff0c;企业处理财税事务常常面临诸多挑战&#xff0c;选择一家靠谱的财务公司至关重要。湖南巨勤财务管理咨询有限公司就是本地正规实体财税服务机构&#xff0c;深耕本地工商财税行业多年&#xff0c;熟悉当地工商局、税务局最新政策与申报流程。主营公司注册、…

还想了解更多?直接咨询顾问

免费诊断 + 免费方案 + 透明报价。

全国咨询热线400-8866-253
免费获取方案
☎咨询二维码 ☎ ↑