LogoLaunchSaaS

电子邮件

使用拆分包架构配置事务性邮件提供商

LaunchSaaS 通过拆分包设计提供邮件支持。核心包 @launchsaas/email 定义接口;每个提供商是独立的包,按需安装。

更新时间:2026-03-15

架构

@launchsaas/email              ← 接口 + Email 类(始终需要)
@launchsaas/email-resend       ← Resend(推荐,支持 Serverless)
@launchsaas/email-nodemailer   ← Nodemailer(SMTP,仅 Node.js)

你只需添加实际使用的提供商包,避免引入不需要的 SDK。

LaunchSaaS 默认使用 @launchsaas/email-resend。在你自己的应用中,可以安装任意偏好的提供商 — Resend、Nodemailer 或自定义包。

设置邮件功能

1. 安装提供商包

在你的应用目录中选择一个提供商:

# Resend(推荐 — 支持 Serverless 和 Edge)
pnpm add @launchsaas/email-resend

# Nodemailer / SMTP(仅限 Node.js 运行时)
pnpm add @launchsaas/email-nodemailer

2. 添加环境变量

将提供商的 keys 导出添加到应用的 env.ts,以便在启动时验证环境变量:

// src/env.ts
import { keys as emailKeys } from "@launchsaas/email-resend/keys";

export const env = createEnv({
  extends: [
    // ... 其他 keys
    emailKeys,
  ],
  // ...
});

然后在 .env 中设置变量:

# Resend
RESEND_API_KEY="re_..."
RESEND_FROM_EMAIL="[email protected]"

# — 或者 — Nodemailer (SMTP)
SMTP_HOST="smtp.example.com"
SMTP_PORT="587"
SMTP_USER="[email protected]"
SMTP_PASS="your-password"
SMTP_FROM_EMAIL="[email protected]"
SMTP_SECURE="false"

3. 在 src/capabilities.ts 中注册

打开你的应用的 src/capabilities.ts,在 email 字段中配置你选择的提供商:

// src/capabilities.ts  (你的应用 — apps/launchsaas/src/capabilities.ts)

// 选项 A — Resend(推荐)
import { ResendEmailProvider } from "@launchsaas/email-resend";
// 选项 B — Nodemailer (SMTP)
// import { NodemailerEmailProvider } from "@launchsaas/email-nodemailer";

export const capabilities = {
  // 设为 null 即可禁用邮件功能
  email: ResendEmailProvider.create(),
  // email: NodemailerEmailProvider.create(),
  // ...其他 capabilities
};

4. 验证是否正常工作

启动开发服务器,触发一封邮件(例如注册获得验证邮件)。检查 Resend Dashboard 或 SMTP 日志。

Resend:域名验证(生产环境)

要从自己的域名发送邮件而非 Resend 测试地址:

  1. 前往 Resend Dashboard 的 Domains
  2. 点击 Add Domain 并输入你的域名(例如 yourdomain.com
  3. 将 Resend 提供的 DNS 记录(MX、TXT/SPF、DKIM)添加到你的 DNS 提供商
  4. 等待 DNS 传播(最多 48 小时),然后点击 Verify
  5. 更新环境变量:RESEND_FROM_EMAIL="[email protected]"

电子邮件模板

LaunchSaaS 使用 packages/design-system/email-templates 中的共享 @launchsaas/email-templates 包渲染事务邮件。apps/email 只是 React Email 预览入口,会复用同一套共享布局,不维护单独的模板实现。生产邮件内容来自 messages/[locale].jsonEmail 命名空间:

模板发送时机
emailVerification用户注册时
resetPassword密码重置流程
magicLink无密码登录
paymentCompleted支付确认
welcome验证完成后的欢迎邮件

i18n 支持

模板自动使用用户保存的语言(按以下顺序回退:请求语言 → 默认 en)。翻译定义在 messages/[locale].jsonEmail 命名空间下:

{
  "Email": {
    "hello": "你好,{name}",
    "emailVerification": {
      "title": "验证你的邮箱",
      "heading": "邮箱验证",
      "action": "验证邮箱",
      "content": "请点击下面的按钮验证你的电子邮件地址。"
    }
  }
}

预览模板

运行邮件预览应用即可在不发送真实邮件的情况下查看所有模板:

pnpm run dev:email
# → http://localhost:3003

预览文件位于 apps/email/emails/。每个文件只提供 mock 数据,并渲染共享的完整邮件布局。

自定义邮件提供商

要集成 LaunchSaaS 未内置的提供商,可创建新的 email-xxx 包:

1. 创建包

mkdir -p packages/capabilities/email-myservice/src

packages/capabilities/email-myservice/package.json

{
  "name": "@launchsaas/email-myservice",
  "version": "0.1.0",
  "private": true,
  "main": "./src/index.ts",
  "exports": {
    ".": "./src/index.ts"
  },
  "dependencies": {
    "@launchsaas/email": "workspace:*",
    "@launchsaas/errors": "workspace:*",
    "@t3-oss/env-nextjs": "^0.13.10",
    "my-email-sdk": "^1.0.0",
    "zod": "^4.0.0"
  }
}

packages/capabilities/email-myservice/src/keys.ts

import { createEnv } from "@t3-oss/env-nextjs";
import { z } from "zod";

export const keys = createEnv({
  server: {
    MYSERVICE_API_KEY: z.string().optional(),
    MYSERVICE_FROM_EMAIL: z.string().optional(),
  },
  experimental__runtimeEnv: {},
});

packages/capabilities/email-myservice/src/provider.ts

import type { EmailProvider, SendEmailOptions } from "@launchsaas/email";

export class MyServiceEmailProvider implements EmailProvider {
  readonly name = "myservice";

  static create(): MyServiceEmailProvider {
    return new MyServiceEmailProvider();
  }

  async send(options: SendEmailOptions): Promise<void> {
    // 在这里调用 my-email-sdk
  }
}

packages/capabilities/email-myservice/src/index.ts

export { MyServiceEmailProvider } from "./provider";
export { keys } from "./keys";

2. 在应用中接入

pnpm add @launchsaas/email-myservice

keys 添加到 env.ts,并在你的应用的 src/capabilities.ts 中注册:

// src/capabilities.ts  (apps/launchsaas/src/capabilities.ts)
import { MyServiceEmailProvider } from "@launchsaas/email-myservice";

export const capabilities = {
  email: MyServiceEmailProvider.create(),
  // ...其他 capabilities
};

禁用邮件功能

若要完全禁用邮件功能,只需在 src/capabilities.ts 中将 email 字段设为 null。依赖邮件的功能(Magic Link、邮箱验证)会自动跳过。

如果禁用了邮件功能,建议同时在 features 配置中设置 magicLink: false,避免用户看到一个静默失败的登录选项。

提供商对比

提供商包名运行时免费额度
Resend@launchsaas/email-resend任意(HTTP)100 封/天
Nodemailer@launchsaas/email-nodemailer仅 Node.js取决于 SMTP 服务商
自定义@launchsaas/email-xxx自定义

参考资料