用 Cloudflare Workers 白嫖一个临时邮箱服务

项目地址:GitHub - cf-tempmail
在线体验:tempemail.mrwuliu.top


开始之前,你需要准备什么

跟着做的话,大概需要下面这些:

  1. 一个 Cloudflare 账户 — 免费注册即可,整个项目依赖 Cloudflare 的免费额度(Workers、KV、Email Routing)

  2. 一个自己的域名 — 需要将域名的 DNS 托管到 Cloudflare,因为 Email Routing 需要在 Cloudflare DNS 上配置 MX 记录。没有域名的话,随便买个便宜的就行(.top 域名一年几块钱)

  3. Node.js 和 npm — 用于安装和运行 Wrangler(Cloudflare Workers 的 CLI 工具)。推荐 Node.js 18+

  4. Rust 工具链(可选) — 如果你也想用 CLI 客户端,需要安装 Rust。用 curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh 一行命令安装

  5. GitHub 账户(可选) — 如果想用本文的自动部署方案,需要一个 GitHub 账户和一个 repo

这些就够了,不用信用卡,也不用服务器。那就开始吧~


起因

某天我为了注册一个「仅需使用一次」的网站,被迫交出了自己的真实邮箱。然后收件箱就被营销邮件淹没了。

这种痛苦经历应该每个人都有过吧?于是我决定自己造一个临时邮箱服务,用完即焚,绝不留痕。

目标很明确:

  • 零成本 — 白嫖 Cloudflare 免费额度

  • 够快 — Workers 边缘计算,全球低延迟

  • 有 CLI — 命令行党也要优雅地收邮件


整体架构

在动手之前,先理清整个数据流:

别人发邮件 → Cloudflare Email Routing → Worker 接收 & 解析 → 存入 KV
                                                        ↓
用户访问网页 / CLI 轮询 ← Worker 读取 KV ← 返回邮件列表

核心就三个组件:

  1. Cloudflare Workers — 当 API 服务器 + 邮件处理器

  2. Cloudflare KV — 当数据库(是的,拿 KV 当数据库)

  3. Rust CLI — 给终端用户用

项目是 monorepo 结构:worker/ 放后端,cli/ 放 Rust 客户端。

做完界面就是这个样子:


第一步:让 Worker 能收邮件

Cloudflare 的 Email Routing 是个神器——它可以把发到 *@yourdomain.com 的邮件全部转发给你处理,而且是免费的。

wrangler.toml 里配好域名和 KV 绑定:

name = "temp-email"
[vars]
EXPIRE_HOURS = "24"
​
[[kv_namespaces]]
binding = "ALIAS_CACHE"
id = "你的KV命名空间ID"

然后在 Cloudflare Dashboard 里设置 Email Routing 的 Catch-all 规则,把所有邮件转发给 Worker。

Worker 需要同时实现两个接口:fetch(HTTP 请求)和 email(邮件接收)。email() 方法会拿到原始的 MIME 邮件数据。


第二步:手搓 MIME 解析器

这是整个项目最「有趣」的部分(指痛不欲生)。

邮件的原始格式是 MIME,长这样:

From: sender@example.com
Subject: =?UTF-8?B?5L2g5aW9?=
Content-Type: text/plain; charset=utf-8
Content-Transfer-Encoding: quoted-printable
​
=E4=BD=A0=E5=A5=BD=E4=B8=96=E7=95=8C

中文会被编码成 =?UTF-8?B?...?=,正文用 quoted-printable 编码。我不得不手写了:

  • quoted-printable 解码 — 把 =E4=BD=A0 这种还原成 UTF-8

  • UTF-8 encoded words 解码 — 处理邮件头里的 =?UTF-8?B?base64?= 格式

  • HTML 剥离 — 有人发 HTML 邮件时提取纯文本

没有用任何邮件解析库,全靠正则和字符串处理。代码丑但能跑。


第三步:设计 KV 存储方案

Cloudflare KV 有个坑爹的限制:list() 操作只能按前缀搜索,而且不能保证一致性。对于邮箱这种需要「列出某别名的所有邮件」的场景,直接用 KV 会很痛苦。

解决方案是 维护一个索引

email_ids:alice123      → ["id1", "id2", "id3"]   // 索引:某别名的所有邮件ID
email:alice123:id1      → {from, subject, body...} // 单封邮件内容

每次收到新邮件,先往索引数组里追加 ID,再存邮件内容。读取时先拿索引,再逐个取邮件。虽然多了一次 KV 读取,但逻辑清晰,完全规避了 list() 的各种坑。

每封邮件还设了 TTL(24 小时自动过期),垃圾邮件自动消失,环保又省心。


第四步:签名认证,无状态鉴权

临时邮箱不需要注册登录,但也不能谁都能看你的邮件。我用了一个简单粗暴的签名方案:

signature = base64(alias + ":" + expireAt + ":" + secretKey)

生成别名时,服务端把签名返回给客户端。之后客户端每次请求都带上这个签名。服务端验证时重新计算签名并比对,同时检查过期时间。

无状态、不需要数据库存 session、自动过期,完美符合临时邮箱的需求。


第五步:捏一个好看的网页

前端直接塞在 Worker 里了——worker.js 里有一整个 HTML 页面,大约 400 行的 inline HTML + Tailwind CSS。

设计风格选了 Neo-Brutalism(新野兽派)

  • 粗黑边框 border-2 border-black

  • 纸张纹理背景

  • 元素微微旋转 rotate(-1deg)

  • 鲜艳的色块

看起来像贴在牛皮纸上的便利贴,有一种手工艺品的质朴感。

功能上:

  • 一键生成临时邮箱

  • 每 5 秒自动刷新收件箱

  • 浏览器通知(新邮件提醒)

  • 一键复制邮箱地址

  • 删除别名

Favicon 是一个内联 SVG 的粉色小花,因为……为什么不能可爱一点呢?


第六步:Rust CLI,终端党的浪漫

临时邮箱只给网页用怎么够?于是我用 Rust 写了个 CLI 客户端。

$ cf-tempmail new
✨ 你的临时邮箱已创建: random-words@mrwuliu.top
📬 签名已保存到配置文件
​
$ cf-tempmail list
📬 收件箱 (2 封邮件)
┌──────────────────────────┬──────────────────────────────┐
│ 发件人                    │ 主题                          │
├──────────────────────────┼──────────────────────────────┤
│ noreply@github.com       │ [GitHub] Verify your email    │
│ hello@some-service.com   │ Welcome to Some Service!      │
└──────────────────────────┴──────────────────────────────┘
​
$ cf-tempmail listen
⏳ 正在监听新邮件... (Ctrl+C 退出)
📧 新邮件来自 noreply@example.com: 验证码是 123456

技术选型:

  • clap 4 — 命令行参数解析(derive 模式,声明式写法很舒服)

  • reqwest + rustls — HTTP 客户端(纯 Rust TLS,不依赖 OpenSSL)

  • colored — 终端彩色输出

  • textwrap — 自动换行对齐

配置文件存在 ~/.config/cf-tempmail/config.toml,存别名和签名,下次直接用。

整个 CLI 只有三文件、约 340 行代码,简洁有力。


第七步:自动部署

最后一步是给 Worker 加上 CI/CD。在 .github/workflows/deploy.yml 里:

on:
  push:
    branches: [main]
jobs:
  deploy:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4
      - uses: cloudflare/wrangler-action@v3
        with:
          apiToken: ${{ secrets.CLOUDFLARE_API_TOKEN }}

推代码到 main 分支,自动部署到 Cloudflare。改完代码 git push 一把梭,完事儿。


最终效果

组件

技术

成本

API 服务器

Cloudflare Workers

免费

数据库

Cloudflare KV

免费

邮件接收

Cloudflare Email Routing

免费

前端

Inline HTML + Tailwind

免费

CLI 客户端

Rust

编译一次到处跑

总成本:0 元/月

访问 tempemail.mrwuliu.top 立即体验,或者装个 CLI 玩玩:

cargo install cf-tempmail-cli

这就是全部了——从零开始,用 Cloudflare 免费资源搭建了一个功能完整的临时邮箱服务。整个过程最有意思的部分是手搓 MIME 解析器和设计新野兽派 UI,最痛苦的部分也是手搓 MIME 解析器。

如果你也想搞一个,fork 我的 repo 改改域名就能用,enjoy!