Rovela 的 API 是单一 JSON 端点,因此从 Python 发送邮件就是一个简单的 HTTP 请求。本指南先演示最简发送,然后加入带幂等键的重试,确保网络抖动时不会产生重复邮件。
准备工作
你需要一个 Rovela 账户(免费,无需绑卡)、仪表盘里的 API 密钥,以及一个已验证的发信域名。本文假设使用 Python 3.7 或更高版本,并已安装 requests 库。同样的方法也适用于标准库的 urllib,或 async 场景下的 httpx,只需替换 HTTP 调用部分即可。
import os
import requests
res = requests.post(
"https://api.rovela.dev/emails",
headers={
"Authorization": f"Bearer {os.environ['ROVELA_API_KEY']}",
"Content-Type": "application/json",
},
json={
"from": "hello@yourdomain.com",
"to": "user@example.com",
"subject": "Welcome aboard",
"html": "<p>Thanks for signing up. Your account is ready.</p>",
},
)
print("Sent:", res.json()["id"])发送第一封邮件
导入 requests 和 os,从环境变量读取 API 密钥,然后向 /emails 端点 POST 一个 JSON 请求体。from 地址必须属于你已验证的域名。响应中包含一个 id,可用于后续查询投递状态。
带幂等键的重试
网络请求会失败,而对超时的安全处理是重试。但如果第一次请求实际上已成功,只是响应丢失了,重试可能会产生第二封邮件。幂等键可以解决这个问题:每次尝试都发送相同的密钥,Rovela 会返回原始响应而不重新发送。在重试循环之前生成密钥,而不是在循环内部生成。
import os
import time
import uuid
import requests
def send_with_retry(payload, retries=3):
key = str(uuid.uuid4())
for i in range(retries + 1):
res = requests.post(
"https://api.rovela.dev/emails",
headers={
"Authorization": f"Bearer {os.environ['ROVELA_API_KEY']}",
"Content-Type": "application/json",
"Idempotency-Key": key, # same key on every attempt
},
json=payload,
)
if res.status_code < 500:
return res # 2xx or 4xx — stop
time.sleep(min(1000 * 2 ** i, 8000) / 1000) # backoff, capped
raise RuntimeError(f"send failed after {retries} retries")环境变量
永远不要把 API 密钥写在源代码里。使用 os.environ 读取密钥,开发环境用 python-dotenv 从 .env 文件加载,生产环境从部署平台的密钥存储读取。如果密钥泄露,在 Rovela 仪表盘中轮换密钥即可;新密钥立即生效,旧密钥随即失效。
常见问题
- 需要 SDK,还是 requests 就够了?
- 直接用 requests 完全可以。Rovela 的 API 是单一 JSON 端点,不需要 SDK。如果你在大型代码库中集成,SDK 可以减少样板代码,但它是可选的。
- 如何发送给多个收件人?
- 在 'to' 字段中传入列表:["alice@example.com", "bob@example.com"]。每个地址会收到邮件的独立副本;各收件人之间互不可见。to、cc 和 bcc 字段均支持字符串或列表。
- 如何同时发送 HTML 和纯文本备选内容?
- 在请求体中同时包含 'html' 和 'text' 字段。无法渲染 HTML 的邮件客户端会显示纯文本版本。Rovela 会自动将两部分打包为 multipart/alternative 格式发送。
- 可以用 httpx 或 aiohttp 做异步发送吗?
- 可以。将 requests.post 替换为对应的 httpx 或 aiohttp 调用即可。请求体和请求头完全相同,只是 HTTP 客户端不同。