forked from datawhale/whale-town-end
7.4 KiB
7.4 KiB
用户认证系统
概述
用户认证系统提供完整的用户注册、登录、密码管理功能,支持传统用户名密码登录和第三方OAuth登录。
功能特性
- 🔐 多种登录方式:用户名/邮箱/手机号登录
- 📝 用户注册和信息管理
- 🐙 GitHub OAuth 第三方登录
- 🔄 密码重置和修改
- 🛡️ bcrypt 密码加密
- 🎯 基于角色的权限控制
架构设计
分层结构
src/
├── business/login/ # 业务逻辑层
│ ├── login.controller.ts # HTTP 控制器
│ ├── login.service.ts # 业务服务
│ ├── login.dto.ts # 数据传输对象
│ ├── login.service.spec.ts # 业务服务测试
│ └── login.module.ts # 业务模块
├── core/
│ ├── login_core/ # 核心功能层
│ │ ├── login_core.service.ts # 核心认证逻辑
│ │ ├── login_core.service.spec.ts # 核心服务测试
│ │ └── login_core.module.ts # 核心模块
│ └── db/users/ # 数据访问层
│ ├── users.entity.ts # 用户实体
│ ├── users.service.ts # 用户数据服务
│ └── users.dto.ts # 用户 DTO
职责分离
1. 业务逻辑层 (Business Layer)
- 位置:
src/business/login/ - 职责:
- 处理HTTP请求和响应
- 数据格式化和验证
- 业务流程控制
- 错误处理和日志记录
2. 核心功能层 (Core Layer)
- 位置:
src/core/login_core/ - 职责:
- 认证核心算法实现
- 密码加密和验证
- 用户查找和匹配
- 令牌生成和验证
3. 数据访问层 (Data Access Layer)
- 位置:
src/core/db/users/ - 职责:
- 数据库操作封装
- 实体关系映射
- 数据完整性保证
- 查询优化
API 接口
用户注册
POST /auth/register
Content-Type: application/json
{
"username": "testuser",
"password": "password123",
"nickname": "测试用户",
"email": "test@example.com",
"phone": "+8613800138000"
}
响应:
{
"success": true,
"data": {
"user": {
"id": "1",
"username": "testuser",
"nickname": "测试用户",
"email": "test@example.com",
"phone": "+8613800138000",
"avatar_url": null,
"role": 1,
"created_at": "2025-12-17T10:00:00.000Z"
},
"access_token": "eyJ1c2VySWQiOiIxIiwidXNlcm5hbWUiOiJ0ZXN0dXNlciJ9...",
"is_new_user": true,
"message": "注册成功"
},
"message": "注册成功"
}
用户登录
POST /auth/login
Content-Type: application/json
{
"identifier": "testuser", # 支持用户名/邮箱/手机号
"password": "password123"
}
GitHub OAuth登录
POST /auth/github
Content-Type: application/json
{
"github_id": "12345678",
"username": "githubuser",
"nickname": "GitHub用户",
"email": "github@example.com",
"avatar_url": "https://avatars.githubusercontent.com/u/12345678"
}
密码重置
# 1. 发送验证码
POST /auth/forgot-password
{
"identifier": "test@example.com"
}
# 2. 重置密码
POST /auth/reset-password
{
"identifier": "test@example.com",
"verification_code": "123456",
"new_password": "newpassword123"
}
修改密码
PUT /auth/change-password
{
"user_id": "1",
"old_password": "password123",
"new_password": "newpassword123"
}
数据模型
用户实体 (Users Entity)
{
id: bigint, // 主键ID
username: string, // 用户名(唯一)
email?: string, // 邮箱(唯一,可选)
phone?: string, // 手机号(唯一,可选)
password_hash?: string, // 密码哈希(OAuth用户为空)
nickname: string, // 显示昵称
github_id?: string, // GitHub ID(唯一,可选)
avatar_url?: string, // 头像URL
role: number, // 用户角色(1-普通,9-管理员)
created_at: Date, // 创建时间
updated_at: Date // 更新时间
}
数据库设计特点
- 唯一性约束: username, email, phone, github_id
- 索引优化: 主键、唯一索引、角色索引
- 字符集支持: utf8mb4,支持emoji
- 数据类型: BIGINT主键,VARCHAR字段,DATETIME时间戳
安全机制
1. 密码安全
- 加密算法: bcrypt (saltRounds=12)
- 强度验证: 最少8位,包含字母和数字
- 存储安全: 只存储哈希值,不存储明文
2. 数据验证
- 输入验证: class-validator装饰器
- SQL注入防护: TypeORM参数化查询
- XSS防护: 数据转义和验证
3. 访问控制
- 令牌机制: 基于用户信息的访问令牌
- 角色权限: 基于角色的访问控制(RBAC)
- 会话管理: 令牌生成和验证
4. 错误处理
- 统一异常: NestJS异常过滤器
- 日志记录: 操作日志和错误日志
- 信息脱敏: 敏感信息自动脱敏
测试覆盖
单元测试
- 核心服务测试:
src/core/login_core/login_core.service.spec.ts - 业务服务测试:
src/business/login/login.service.spec.ts
集成测试
- 端到端测试:
test/business/login.e2e-spec.ts
测试用例
- 用户注册和登录流程
- GitHub OAuth认证
- 密码重置和修改
- 数据验证和错误处理
- 安全性测试
使用示例
JavaScript/TypeScript
// 用户注册
const registerResponse = await fetch('/auth/register', {
method: 'POST',
headers: {
'Content-Type': 'application/json',
},
body: JSON.stringify({
username: 'testuser',
password: 'password123',
nickname: '测试用户',
email: 'test@example.com'
})
});
const registerData = await registerResponse.json();
console.log(registerData);
// 用户登录
const loginResponse = await fetch('/auth/login', {
method: 'POST',
headers: {
'Content-Type': 'application/json',
},
body: JSON.stringify({
identifier: 'testuser',
password: 'password123'
})
});
const loginData = await loginResponse.json();
console.log(loginData);
curl 命令
# 用户注册
curl -X POST http://localhost:3000/auth/register \
-H "Content-Type: application/json" \
-d '{
"username": "testuser",
"password": "password123",
"nickname": "测试用户",
"email": "test@example.com"
}'
# 用户登录
curl -X POST http://localhost:3000/auth/login \
-H "Content-Type: application/json" \
-d '{
"identifier": "testuser",
"password": "password123"
}'
错误处理
常见错误代码
LOGIN_FAILED: 登录失败REGISTER_FAILED: 注册失败GITHUB_OAUTH_FAILED: GitHub登录失败SEND_CODE_FAILED: 发送验证码失败RESET_PASSWORD_FAILED: 密码重置失败CHANGE_PASSWORD_FAILED: 密码修改失败
错误响应格式
{
"success": false,
"message": "错误描述",
"error_code": "ERROR_CODE"
}
扩展功能
计划中的功能
-
JWT令牌管理
- 访问令牌和刷新令牌
- 令牌黑名单机制
- 自动刷新功能
-
多因子认证
- 短信验证码
- 邮箱验证码
- TOTP应用支持
-
社交登录扩展
- 微信登录
- QQ登录
- 微博登录
-
安全增强
- 登录失败次数限制
- IP白名单/黑名单
- 设备指纹识别
-
用户管理
- 用户状态管理(激活/禁用)
- 用户角色权限细化
- 用户行为日志记录