@saleandwin/mfa
v1.0.1
Published
Multi-Factor Authentication (MFA) module for framework-ts projects with TOTP support
Maintainers
Readme
@saleandwin/mfa
多因子认证 (MFA) 模块,为 framework-ts 项目提供 TOTP 认证功能。
✨ 特性
- 🔐 TOTP 认证 - 支持 Google Authenticator、Authy 等应用
- 🔑 备用码 - 提供备用恢复码
- 📱 二维码生成 - 自动生成绑定二维码
- 🛡️ 安全设计 - 密钥加密存储,完整审计日志
- 🚀 Cloudflare Workers 优化 - 专为 Workers 环境设计
- 📊 统计分析 - 完整的使用统计和审计功能
📦 安装
npm install @saleandwin/mfa
# 或
pnpm add @saleandwin/mfa🚀 快速开始
1. 基础配置
import { MfaHandler, type MfaConfig, type MfaEnv } from '@saleandwin/mfa';
// 在 Cloudflare Workers 中
export default {
async fetch(request: Request, env: MfaEnv, ctx: ExecutionContext): Promise<Response> {
const config: MfaConfig = {
issuer: 'Your App',
service_name: 'Your Service',
totp_window: 1,
backup_codes_count: 10,
require_mfa: false
};
// 创建 MFA Handler 实例
const mfaHandler = MfaHandler.createInstance(config, env);
// 处理请求...
}
};2. 数据库初始化
# 执行数据库迁移
wrangler d1 execute your-database --file=./node_modules/@saleandwin/mfa/migrations.sql📖 API 文档
核心方法
1. 生成 TOTP 绑定信息
const result = await mfaHandler.handleGenerateTotpBinding({
user_id: 'user-123',
issuer: 'My App', // 可选
service_name: 'My Service' // 可选
});
if (result.success) {
console.log('绑定信息:', result.data);
// {
// secret: 'JBSWY3DPEHPK3PXP',
// qr_code: 'base64-encoded-qr-image',
// manual_entry_key: 'JBSW Y3DP EHPK 3PXP',
// backup_codes: ['12345678', '87654321', ...]
// }
}2. 绑定验证
const result = await mfaHandler.handleBindVerification({
user_id: 'user-123',
secret: 'JBSWY3DPEHPK3PXP',
verification_code: '123456'
});
if (result.success) {
console.log('MFA 绑定成功');
}3. 验证码校验
const result = await mfaHandler.handleVerifyCode({
user_id: 'user-123',
verification_code: '123456' // TOTP 验证码或备用码
});
if (result.valid) {
console.log('验证成功');
} else {
console.log('验证失败:', result.error);
}4. 解绑 MFA
const result = await mfaHandler.handleUnbindMfa({
user_id: 'user-123',
verification_code: '123456' // 可选,用于验证身份
});
if (result.success) {
console.log('MFA 解绑成功');
}5. 获取 MFA 状态
const result = await mfaHandler.handleGetMfaStatus('user-123');
if (result.success) {
console.log('MFA 状态:', result.data);
// {
// enabled: true,
// status: 'enabled',
// enabled_at: '2024-01-01T00:00:00.000Z',
// last_used_at: '2024-01-01T12:00:00.000Z',
// available_backup_codes: 8
// }
}🔧 配置选项
interface MfaConfig {
issuer: string; // TOTP 发行者名称
service_name: string; // 服务名称
totp_window: number; // TOTP 时间窗口(默认:1)
backup_codes_count: number; // 备用码数量(默认:10)
require_mfa: boolean; // 是否强制要求 MFA(默认:false)
}🛡️ 安全特性
1. 密钥安全
- TOTP 密钥加密存储
- 备用码哈希存储
- 防止密钥泄露
2. 验证安全
- 时间窗口验证
- 防重放攻击
- 失败次数限制
3. 审计日志
- 完整的操作记录
- IP 地址和用户代理记录
- 成功/失败状态追踪
📊 使用场景
1. 用户登录增强
// 在用户登录后检查是否需要 MFA
const mfaCheck = await mfaHandler.handleCheckMfaRequired(userId);
if (mfaCheck.required) {
// 要求用户输入 MFA 验证码
const mfaResult = await mfaHandler.handleVerifyCode({
user_id: userId,
verification_code: userInput
});
if (!mfaResult.valid) {
return new Response('MFA 验证失败', { status: 401 });
}
}2. 敏感操作保护
// 在执行敏感操作前要求 MFA 验证
async function handleSensitiveOperation(userId: string, mfaCode: string) {
const mfaResult = await mfaHandler.handleVerifyCode({
user_id: userId,
verification_code: mfaCode
});
if (!mfaResult.valid) {
throw new Error('需要 MFA 验证');
}
// 执行敏感操作...
}🔄 与 Auth 模块集成
import { AuthHandler } from '@saleandwin/auth';
import { MfaHandler } from '@saleandwin/mfa';
export default {
async fetch(request: Request, env: any, ctx: ExecutionContext): Promise<Response> {
const authHandler = AuthHandler.createInstance(authConfig, env);
const mfaHandler = MfaHandler.createInstance(mfaConfig, env);
// 处理登录
if (url.pathname === '/auth/login') {
const loginResult = await authHandler.handleLogin(loginData);
if (loginResult.success) {
// 检查是否需要 MFA
const mfaCheck = await mfaHandler.handleCheckMfaRequired(loginResult.data.user.id);
if (mfaCheck.required) {
return Response.json({
success: true,
require_mfa: true,
user_id: loginResult.data.user.id
});
}
}
return Response.json(loginResult);
}
// 处理 MFA 验证
if (url.pathname === '/auth/mfa/verify') {
const mfaResult = await mfaHandler.handleVerifyCode(mfaData);
return Response.json(mfaResult);
}
}
};📱 客户端集成
1. 绑定流程
// 1. 获取绑定信息
const bindingResponse = await fetch('/mfa/generate-binding', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ user_id: 'user-123' })
});
const bindingData = await bindingResponse.json();
// 2. 显示二维码
const qrImage = document.getElementById('qr-code');
qrImage.src = `data:image/png;base64,${bindingData.data.qr_code}`;
// 3. 显示手动输入密钥
document.getElementById('manual-key').textContent = bindingData.data.manual_entry_key;
// 4. 用户扫码后输入验证码进行绑定
const verifyResponse = await fetch('/mfa/bind-verify', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({
user_id: 'user-123',
secret: bindingData.data.secret,
verification_code: userInputCode
})
});2. 验证流程
// MFA 验证
const verifyResponse = await fetch('/mfa/verify', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({
user_id: 'user-123',
verification_code: userInputCode
})
});
const result = await verifyResponse.json();
if (result.valid) {
// 验证成功,继续操作
} else {
// 验证失败,显示错误
}🧪 测试
# 运行测试
pnpm test
# 运行测试覆盖率
pnpm test:coverage� 谷歌验证器支持
MFA 模块完全支持谷歌验证器的多账户管理功能,让用户可以在一个应用中管理多个服务的 TOTP 密钥。
核心功能
1. 添加密钥
const result = await mfaHandler.handleAddSecret({
user_id: 'user-123',
secret_key: 'JBSWY3DPEHPK3PXP',
label: 'Google',
issuer: 'Google'
});2. 生成所有验证码
const codesResult = await mfaHandler.handleGenerateAllCodes('user-123');
if (codesResult.success) {
codesResult.codes?.forEach((codeInfo) => {
console.log(`${codeInfo.label}: ${codeInfo.code} (${codeInfo.remaining_seconds}s)`);
});
}3. 密钥管理
// 获取密钥列表
const secretsResult = await mfaHandler.handleGetUserSecrets('user-123');
// 删除密钥
const deleteResult = await mfaHandler.handleDeleteSecret('user-123', 'secret-id');应用场景
- 个人密码管理器 - 用户管理多个账户的 MFA
- 企业应用 - 员工管理工作相关的多个服务
- 开发者工具 - 集成到现有应用中提供 MFA 功能
- 移动应用 - 替代谷歌验证器的功能
特性优势
- ✅ 多账户支持 - 一个用户可以管理多个服务的密钥
- ✅ 实时验证码 - 显示当前验证码和剩余时间
- ✅ 标签管理 - 为每个密钥设置有意义的标签
- ✅ 批量生成 - 一次性生成所有账户的验证码
- ✅ 完整 CRUD - 支持密钥的增删改查操作
- ✅ 安全存储 - 密钥加密存储,完整审计日志
�📄 许可证
MIT License
🤝 贡献
欢迎提交 Issue 和 Pull Request!
