每千封邮件仅需 $0.10 — 迄今最具性价比的正规邮件 API。代价是更多 AWS 风格的配置(IAM、沙盒模式退出申请、按区域 DNS 验证),以及相比开发者优先服务略显粗糙的体验。适合在 AWS 生态内、对规模化单封邮件成本极度敏感的场景。
登录 AWS 控制台,搜索 SES,选择离用户最近的区域(如 us-east-1)。SES 控制台 ↗。
SES 是按区域隔离的 — 验证信息和发送统计不跨区域共享。选定一个区域后请保持一致。
SES → 已验证身份 → 创建身份 → 域。输入你的域名,选择 Easy DKIM(RSA-2048)。
SES 会生成 3 条 CNAME 记录,将它们添加到你的 DNS 服务商处。SES 每 24 小时自动检测一次,通常在一小时内完成验证。
你也可以验证单个邮件地址(用于测试):创建身份 → 电子邮件地址 → AWS 发送确认链接。操作简便但有限制;生产环境应使用域名验证。
新 SES 账户默认处于沙盒模式:
这是 AWS 在你向陌生人发送邮件之前对你进行审核的机制。要退出沙盒,点击 账户面板 → 申请生产访问权限,填写表单:
AWS 通常在 24 小时内响应,有时仅需几分钟。审批通过后初始上限为每天 5 万封,随声誉积累自动提升。
不要使用 AWS 根凭证。创建一个拥有最小权限策略的 IAM 用户:
ses-sender-prod(或类似名称)。ses:SendEmail + ses:SendRawEmail 的内联策略进一步收紧权限)。将访问密钥和私密密钥保存到环境变量:
AWS_ACCESS_KEY_ID=AKIAxxxxxxxxxxxxxxxx
AWS_SECRET_ACCESS_KEY=xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
AWS_REGION=us-east-1
如果你的应用已在 AWS 上运行(EC2、Lambda 等),请使用 IAM 角色替代长期凭证,这是 AWS 标准实践。
npm install @aws-sdk/client-sesv2
SES 有 v1 和 v2 两套 API,请使用 v2 — 更新、默认值更合理、支持所有当前功能。其他语言:boto3、AWS SDK for Java、Go、.NET ↗。
import {
SESv2Client,
SendEmailCommand,
} from "@aws-sdk/client-sesv2";
const ses = new SESv2Client({ region: process.env.AWS_REGION });
await ses.send(new SendEmailCommand({
FromEmailAddress: "[email protected]",
Destination: { ToAddresses: ["[email protected]"] },
Content: {
Simple: {
Subject: { Data: "Hello from AWS SES" },
Body: {
Text: { Data: "Plain text version" },
Html: { Data: "<p>HTML body</p>" },
},
},
},
}));
AWS SDK 会自动从环境变量或 IAM 角色读取凭证。可在 SES 控制台 → 声誉指标中查看发送统计。
AWS 会暂停你的 SES 账户,若退信率超过 5% 或投诉率超过 0.1%。你必须处理这些信号。
标准配置:
default-prod。每次发送时传入配置集名称:
await ses.send(new SendEmailCommand({
FromEmailAddress: "[email protected]",
Destination: { ToAddresses: ["..."] },
Content: { /* ... */ },
ConfigurationSetName: "default-prod",
}));
不配置此项,账户迟早会被暂停。这一步不可省略。
SES 支持类 Mustache 语法的服务端模板。创建模板:
import { CreateEmailTemplateCommand } from "@aws-sdk/client-sesv2";
await ses.send(new CreateEmailTemplateCommand({
TemplateName: "welcome",
TemplateContent: {
Subject: "Welcome to {{appName}}",
Html: "<p>Hi {{name}}, welcome!</p>",
Text: "Hi {{name}}, welcome!",
},
}));
使用模板发送:
import { SendEmailCommand } from "@aws-sdk/client-sesv2";
await ses.send(new SendEmailCommand({
FromEmailAddress: "[email protected]",
Destination: { ToAddresses: [user.email] },
Content: {
Template: {
TemplateName: "welcome",
TemplateData: JSON.stringify({ name: user.name, appName: "MyApp" }),
},
},
}));
SES 模板功能可用,但编辑体验较为简陋。许多团队选择在应用内渲染 HTML(用 React Email、MJML 或类似工具),再将渲染结果作为字符串传给 Simple.Body.Html。
SES 也提供 SMTP 凭证,适用于只支持 SMTP 协议的软件(如 WordPress、Postfix 中继、老旧系统)。
SES 控制台 → SMTP 设置 → 创建 SMTP 凭证。系统会生成专用于 SMTP 的用户名和密码。连接信息:
Host: email-smtp.us-east-1.amazonaws.com
Port: 587 (STARTTLS) or 465 (SSL)
Auth: the username/password just generated
SES 控制台 → 声誉指标:
为这些指标设置 CloudWatch 告警。配置得当后,AWS 会在暂停前提前通知你。若不设告警,你只会在发送中断时才发现问题。
ses:SendEmail 权限,更新策略即可。每 1,000 封外发邮件收费 $0.10;每 1,000 封接收邮件收费 $0.10(如启用接收);附件每 GB 收费 $0.12。
免费额度:从 EC2 实例发送时,每月可免费发送 62,000 封邮件。其他情况从第 1 封起计费(但 $0.10/千封已经足够便宜,差异几乎可以忽略)。