Files
backend/.qoder/repowiki/zh/content/API参考/认证API/重置密码.md
lan a4b6c5011e
Some checks failed
SonarQube Analysis / sonarqube (push) Has been cancelled
chore(git): 更新.gitignore以忽略新的本地文件
2025-11-30 08:33:17 +08:00

343 lines
13 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# 重置密码
<cite>
**本文引用的文件**
- [internal/handler/auth_handler.go](file://internal/handler/auth_handler.go)
- [internal/handler/routes.go](file://internal/handler/routes.go)
- [internal/service/verification_service.go](file://internal/service/verification_service.go)
- [internal/service/user_service.go](file://internal/service/user_service.go)
- [pkg/auth/password.go](file://pkg/auth/password.go)
- [internal/types/common.go](file://internal/types/common.go)
- [internal/model/response.go](file://internal/model/response.go)
</cite>
## 目录
1. [简介](#简介)
2. [项目结构](#项目结构)
3. [核心组件](#核心组件)
4. [架构总览](#架构总览)
5. [详细组件分析](#详细组件分析)
6. [依赖关系分析](#依赖关系分析)
7. [性能考量](#性能考量)
8. [故障排查指南](#故障排查指南)
9. [结论](#结论)
10. [附录](#附录)
## 简介
本文件面向开发者与测试人员系统化梳理“重置密码”API的完整实现与使用规范覆盖以下要点
- 接口定位与HTTP方法POST /api/v1/auth/reset-password
- 请求体字段与校验规则email、verificationCode、newPassword
- 响应格式与错误码:统一的业务状态码与错误消息
- 流程说明:验证码验证 → 密码加密更新 → 成功响应
- 安全考虑:验证码一次性使用、有效期控制、密码复杂度要求
## 项目结构
围绕“重置密码”的关键文件分布如下:
- 路由注册:在路由组中将 /api/v1/auth/reset-password 绑定到处理器
- 处理器:接收请求、绑定参数、调用服务层、返回统一响应
- 服务层:
- 验证码服务:生成、发送、验证、删除;验证码一次性使用与有效期控制
- 用户服务:根据邮箱查找用户并更新密码(密码经加密后持久化)
- 工具与模型:
- 密码工具bcrypt 加密与校验
- 请求类型ResetPasswordRequest 的字段与约束
- 响应模型:统一响应结构与常用状态码
```mermaid
graph TB
subgraph "接口层"
R["路由注册<br/>/api/v1/auth/reset-password"]
H["处理器<br/>ResetPassword"]
end
subgraph "服务层"
VS["验证码服务<br/>VerifyCode/Generate/Send/Delete"]
US["用户服务<br/>ResetUserPassword"]
end
subgraph "工具与模型"
PW["密码工具<br/>bcrypt 加密/校验"]
RT["请求类型<br/>ResetPasswordRequest"]
RM["响应模型<br/>统一响应/状态码"]
end
R --> H
H --> VS
H --> US
US --> PW
H --> RM
VS --> RM
RT --> H
```
图表来源
- [internal/handler/routes.go](file://internal/handler/routes.go#L16-L26)
- [internal/handler/auth_handler.go](file://internal/handler/auth_handler.go#L194-L249)
- [internal/service/verification_service.go](file://internal/service/verification_service.go#L40-L98)
- [internal/service/user_service.go](file://internal/service/user_service.go#L166-L184)
- [pkg/auth/password.go](file://pkg/auth/password.go#L1-L21)
- [internal/types/common.go](file://internal/types/common.go#L55-L61)
- [internal/model/response.go](file://internal/model/response.go#L1-L86)
章节来源
- [internal/handler/routes.go](file://internal/handler/routes.go#L16-L26)
- [internal/handler/auth_handler.go](file://internal/handler/auth_handler.go#L194-L249)
## 核心组件
- 接口路径与方法
- 方法POST
- 路径:/api/v1/auth/reset-password
- 请求体结构
- 字段:
- email字符串必填需符合邮箱格式
- verificationCode字符串必填长度必须为6
- newPassword字符串必填长度范围为6~128
- 校验来源:请求类型定义与处理器绑定校验
- 响应格式
- 成功统一响应结构code=200message=“操作成功”data为空或简要提示
- 失败:统一错误响应结构,包含业务状态码与错误消息
- 错误码
- 400请求参数错误如字段缺失、格式不符、长度不符
- 400验证码错误或已过期
- 500服务端内部错误如数据库异常
章节来源
- [internal/handler/auth_handler.go](file://internal/handler/auth_handler.go#L194-L249)
- [internal/types/common.go](file://internal/types/common.go#L55-L61)
- [internal/model/response.go](file://internal/model/response.go#L27-L52)
## 架构总览
下图展示“重置密码”端到端调用链路与各模块职责。
```mermaid
sequenceDiagram
participant C as "客户端"
participant G as "Gin路由"
participant H as "处理器 ResetPassword"
participant VS as "验证码服务 VerifyCode"
participant US as "用户服务 ResetUserPassword"
participant PW as "密码工具 bcrypt"
participant DB as "数据库"
C->>G : "POST /api/v1/auth/reset-password"
G->>H : "路由转发"
H->>H : "绑定并校验请求体"
H->>VS : "VerifyCode(email, code, type=reset_password)"
VS-->>H : "验证通过/失败"
alt "验证码失败"
H-->>C : "400 错误响应"
else "验证码通过"
H->>US : "ResetUserPassword(email, newPassword)"
US->>PW : "HashPassword(newPassword)"
PW-->>US : "hashedPassword"
US->>DB : "UpdateUserFields(password=hashed)"
DB-->>US : "OK"
US-->>H : "OK"
H-->>C : "200 成功响应"
end
```
图表来源
- [internal/handler/auth_handler.go](file://internal/handler/auth_handler.go#L194-L249)
- [internal/service/verification_service.go](file://internal/service/verification_service.go#L79-L98)
- [internal/service/user_service.go](file://internal/service/user_service.go#L166-L184)
- [pkg/auth/password.go](file://pkg/auth/password.go#L1-L21)
## 详细组件分析
### 处理器ResetPassword
- 职责
- 绑定并校验请求体
- 调用验证码服务验证验证码(一次性使用)
- 调用用户服务更新密码(密码加密存储)
- 返回统一响应
- 关键行为
- 参数绑定失败返回400
- 验证码失败返回400
- 更新密码失败返回500
- 成功返回200
章节来源
- [internal/handler/auth_handler.go](file://internal/handler/auth_handler.go#L194-L249)
### 验证码服务VerifyCode 与发送流程
- 验证码类型
- reset_password用于重置密码场景
- 一次性使用
- 验证通过后立即删除Redis中的验证码键值
- 有效期控制
- 默认10分钟
- 发送频率限制
- 同一邮箱同类型验证码在1分钟内不可重复发送
- 发送流程
- 生成6位数字验证码
- 写入Redis带过期时间
- 设置发送频率限制键
- 发送邮件(按类型区分模板)
```mermaid
flowchart TD
Start(["开始"]) --> Bind["绑定请求体"]
Bind --> Verify["VerifyCode(email, code, type)"]
Verify --> Check{"验证码正确且未过期?"}
Check --> |否| Err["返回400 错误"]
Check --> |是| Delete["删除Redis中的验证码键"]
Delete --> Next["进入下一步"]
Err --> End(["结束"])
Next --> End
```
图表来源
- [internal/handler/auth_handler.go](file://internal/handler/auth_handler.go#L218-L230)
- [internal/service/verification_service.go](file://internal/service/verification_service.go#L79-L98)
章节来源
- [internal/service/verification_service.go](file://internal/service/verification_service.go#L14-L24)
- [internal/service/verification_service.go](file://internal/service/verification_service.go#L40-L98)
### 用户服务ResetUserPassword
- 流程
- 根据邮箱查询用户
- 对新密码进行bcrypt加密
- 更新用户记录的password字段
- 错误处理
- 用户不存在:返回错误
- 加密失败:返回错误
- 数据库更新失败:返回错误
```mermaid
flowchart TD
S(["开始"]) --> Find["根据邮箱查找用户"]
Find --> Found{"找到用户?"}
Found --> |否| E1["返回错误:用户不存在"]
Found --> |是| Hash["HashPassword(newPassword)"]
Hash --> HOK{"加密成功?"}
HOK --> |否| E2["返回错误:密码加密失败"]
HOK --> |是| Update["UpdateUserFields(password=hashed)"]
Update --> UOK{"更新成功?"}
UOK --> |否| E3["返回错误:数据库更新失败"]
UOK --> |是| OK["返回成功"]
E1 --> End(["结束"])
E2 --> End
E3 --> End
OK --> End
```
图表来源
- [internal/service/user_service.go](file://internal/service/user_service.go#L166-L184)
- [pkg/auth/password.go](file://pkg/auth/password.go#L1-L21)
章节来源
- [internal/service/user_service.go](file://internal/service/user_service.go#L166-L184)
- [pkg/auth/password.go](file://pkg/auth/password.go#L1-L21)
### 请求体与响应模型
- 请求体字段与约束
- email必填邮箱格式
- verificationCode必填长度6
- newPassword必填长度6~128
- 响应模型
- 成功code=200message=“操作成功”
- 失败code=400或500message=错误描述
章节来源
- [internal/types/common.go](file://internal/types/common.go#L55-L61)
- [internal/model/response.go](file://internal/model/response.go#L27-L52)
## 依赖关系分析
- 路由到处理器
- /api/v1/auth/reset-password → ResetPassword
- 处理器到服务层
- ResetPassword → VerifyCode验证码验证
- ResetPassword → ResetUserPassword密码更新
- 服务层到工具
- ResetUserPassword → HashPasswordbcrypt加密
- 服务层到存储
- ResetUserPassword → UpdateUserFields持久化
```mermaid
graph LR
Routes["路由"] --> Handler["处理器 ResetPassword"]
Handler --> VS["验证码服务"]
Handler --> US["用户服务"]
US --> PW["密码工具 bcrypt"]
US --> DB["数据库"]
```
图表来源
- [internal/handler/routes.go](file://internal/handler/routes.go#L16-L26)
- [internal/handler/auth_handler.go](file://internal/handler/auth_handler.go#L194-L249)
- [internal/service/verification_service.go](file://internal/service/verification_service.go#L79-L98)
- [internal/service/user_service.go](file://internal/service/user_service.go#L166-L184)
- [pkg/auth/password.go](file://pkg/auth/password.go#L1-L21)
章节来源
- [internal/handler/routes.go](file://internal/handler/routes.go#L16-L26)
- [internal/handler/auth_handler.go](file://internal/handler/auth_handler.go#L194-L249)
- [internal/service/verification_service.go](file://internal/service/verification_service.go#L79-L98)
- [internal/service/user_service.go](file://internal/service/user_service.go#L166-L184)
- [pkg/auth/password.go](file://pkg/auth/password.go#L1-L21)
## 性能考量
- 验证码存储与访问
- Redis作为验证码缓存具备高并发读写能力建议合理设置过期时间与限流键避免热点攻击
- 密码加密成本
- bcrypt默认成本较高单次加密有一定CPU开销建议在高并发场景下关注服务实例的CPU占用与延迟
- 数据库更新
- 单字段更新通常很快;建议确保数据库连接池配置合理,避免阻塞
## 故障排查指南
- 常见错误与定位
- 400 参数错误:检查请求体字段是否齐全、格式是否正确、长度是否满足约束
- 400 验证码错误/过期:确认验证码是否正确、是否已被使用(一次性)、是否超过有效期
- 500 服务器错误:检查用户是否存在、密码加密是否成功、数据库更新是否异常
- 日志与追踪
- 处理器对失败场景会输出警告/错误日志,便于定位问题
- 验证码生命周期
- 验证通过即删除,确保验证码只能使用一次
- 过期时间为10分钟超过后无法再使用
章节来源
- [internal/handler/auth_handler.go](file://internal/handler/auth_handler.go#L218-L249)
- [internal/service/verification_service.go](file://internal/service/verification_service.go#L79-L98)
## 结论
“重置密码”API以清晰的职责划分与严格的参数校验保障了安全性与可用性。验证码一次性使用与有效期控制有效降低了滥用风险密码采用bcrypt加密存储符合安全最佳实践。统一的响应模型与错误码体系提升了接口一致性与可观测性。
## 附录
### 请求与响应示例
- 请求示例JSON
- POST /api/v1/auth/reset-password
- Body
- email字符串必填邮箱格式
- verificationCode字符串必填长度6
- newPassword字符串必填长度6~128
- 成功响应示例JSON
- Status200
- Body
- code200
- message“操作成功”
- data空对象或简要提示
- 失败响应示例JSON
- Status400 或 500
- Body
- code400 或 500
- message错误描述
- error详细错误信息开发环境
章节来源
- [internal/types/common.go](file://internal/types/common.go#L55-L61)
- [internal/model/response.go](file://internal/model/response.go#L27-L52)
- [internal/handler/auth_handler.go](file://internal/handler/auth_handler.go#L218-L249)
### 安全考虑
- 验证码一次性使用
- 验证通过后立即删除Redis中的验证码键防止复用
- 验证码有效期控制
- 默认10分钟超时即失效
- 发送频率限制
- 同一邮箱同类型验证码在1分钟内不可重复发送
- 密码复杂度要求
- newPassword长度范围为6~128建议结合业务策略进一步增强复杂度例如包含大小写字母、数字与特殊字符当前实现以长度约束为主
章节来源
- [internal/service/verification_service.go](file://internal/service/verification_service.go#L14-L24)
- [internal/service/verification_service.go](file://internal/service/verification_service.go#L40-L98)
- [internal/types/common.go](file://internal/types/common.go#L55-L61)