bujinyuan
|
096563d3ea
|
feat(phase2e-2): WebSocket 信令协议 13 事件全量落地(Task 6)
将 meeting.* 事件族从 Task 5 的 PublishToUser 循环升级为完整 WS 信令协议:
抽离统一广播层、扩容 MediaOrchestrator 接口、实现 8 个 C→S 事件业务逻辑
+ Redis 资源追踪 + host 权限校验,端到端 18/18 PASS。
核心产出:
- 新建 MeetingBroadcaster(统一广播层,REST/WS 共用)
- 新建 MeetingSignalService 8 C→S 事件 + cleanupUserResources
- 新建 MeetingWSHandler 薄层 controller
- MediaOrchestrator 扩容 9 方法 + NoopMediaOrchestrator 占位(Task 7 替换)
- C→S 白名单机制防恶意伪造广播事件
- Redis Set 资源追踪防 mediasoup 端资源泄漏
文档同步:
- docs/api/frontend/meeting.md 追加 §WebSocket 信令协议(Task 6)200 行
- docs/progress/CURRENT_STATUS.md + project-context.mdc + 实施计划 Task 6 ✅
Made-with: Cursor
|
2026-04-21 17:10:32 +08:00 |
|
bujinyuan
|
e235e001b3
|
feat(phase2e-2): Go meeting 模块 12 个 REST 接口业务逻辑全量落地(Task 5)
主要产出:
- DTO 层:app/dto/meeting_dto.go 完整定义 13 个 DTO(请求/响应/基础共用)
- Service 层:MeetingService 12 业务方法 + 11 个 sentinel 错误 + 4 辅助
- CreateRoom/JoinRoom/LeaveRoom/EndRoom 核心生命周期
- KickMember/TransferHost/GetRoom/ListMyMeetings 会议管理
- InviteUsers(+ NotifyPusher)/ RedeemInviteToken 邀请链路
- SendChat/ListChats 会议内聊天
- Controller 层:12 handler + handleError 领域错误 → HTTP 映射
- 工具层:pkg/utils/meeting_code.go(XXX-XXX-XXX + invite token)
- Stub 接口:MediaOrchestrator(Task 7 替换)+ NoopMediaOrchestrator
- 路径修正:/rooms → /rooms/mine、/invites → /invite-tokens 对齐设计
- DAO 契约修复:GetByID/GetByCode/GetByRoomAndUser/FindActiveByUser
将 gorm.ErrRecordNotFound 转为 (nil, nil),service 统一 nil 判定
- 安全强化:密码 bcrypt + 5 次错误锁 10 分钟;邀请 token 仅通过
NotifyPusher.Extra 定向下发,响应不回传
- host 自动转让:host 离会时将最早加入者提升为 host
- 单点参会:用户同一时间仅能在一个活跃会议
- API 文档:docs/api/frontend/meeting.md 重写为 12 接口完整规范
- Wire 依赖注入:MediaOrchestrator + NoopMediaOrchestrator provider
验证:
- go build / go vet / wire 零告警
- 端到端 3 用户场景:12 happy path + 5 错误路径 PASS=19 / FAIL=0
覆盖密码错/房间不存在/单点冲突/越权/邀请失效
文档同步:
- docs/progress/CURRENT_STATUS.md 增补 Task 5 章节
- .cursor/rules/project-context.mdc 更新阶段状态
- docs/plans/2026-04-21-phase2e-2-implementation.plan.md 标记 T5 ✅
下一步:Task 6(WS 信令协议 + BroadcastToMeeting 替换 PublishToUser 循环)
Made-with: Cursor
|
2026-04-21 16:39:59 +08:00 |
|
bujinyuan
|
d22f61fb9b
|
feat(phase2e-2): Go meeting 模块 DDL + Model + DAO + service/controller/router 骨架(Task 3+4)
Task 3 - 数据库与持久化层:
- init.sql 追加 3 张表(meeting_rooms / meeting_participants / meeting_chats)+ 9 索引 + 全量 COMMENT
- 新增 phase2e2_migration.sql 增量升级脚本(IF NOT EXISTS 幂等)
- app/constants/meeting.go 统一会议常量(类型/状态/角色/结束原因/离会原因/默认配置/WS 事件 8 组)
- app/meeting/model 3 个 model + GORM tag(TIMESTAMP(0) 对齐现有表风格)
- app/meeting/dao 3 个 DAO 共 24 个方法:
* meeting_room_dao:Create/Get/Exists/MarkStarted/MarkEnded(乐观锁)/UpdateHost/UpdateSettings/ListByHost/ListExpiredForCleanup
* meeting_participant_dao:JoinRoom(事务内复用旧记录)/LeaveRoom(EXTRACT(EPOCH) DB 时间)/LeaveAllActive/TransferHost(事务)/FindActiveByUser(JOIN 单点校验)/列表计数更新
* meeting_chat_dao:Create/ListByRoom(游标)/DeleteByRoomIDs/CountByRoom
- psql 真库跑通 CRUD + UNIQUE + CASCADE + 主持人转让事务 + duration=10s 精确匹配 8 场景
Task 4 - Go 侧 service/controller/router/wire 骨架:
- app/meeting/service/interfaces.go:NotifyPusher / UserInfoResolver / OnlineChecker 三接口(解耦 notify/contact/ws)
- app/meeting/service/meeting_service.go:MeetingService + 8 sentinel error + 17 个空方法(返回 ErrNotImplemented)
- app/meeting/controller/meeting_controller.go:12 个 Gin handler + responseNotImplemented(501)
- app/meeting/router.go:12 条路由挂 /api/v1/meeting/* 并套 jwtAuth(扁平化 router.go,与 group/notify 一致)
- app/meeting/provider.go:MeetingSet = wire.NewSet(DAO×3, Service, Controller)
- 全局 wire.go 挂入 MeetingSet + 3 条 wire.Bind(Notify/UserInfo/Online);App struct/NewApp 加字段;router/router.go 挂载
- 存量修复:admin/provider.go 补齐 MessageManage{DAO,Service,Controller} 解决旧版 wire 重生成报 no provider found
- 验证:go build ./... / go vet ./... / wire ./app/provider 零错误;GIN_MODE=debug 启动打印全部 12 条路由;无 token curl 3 条代表性路由均返回 401(JWT 中间件生效)
关键风格修正(偏离草案):
- 常量归入 app/constants/meeting.go 单文件(与 group.go / notify.go 同构),非草案 app/meeting/constants/
- TIMESTAMP(0) 取代草案 TIMESTAMPTZ 对齐所有现有表
- 冗余 idx_meeting_rooms_code 移除(UNIQUE 已自动建索引)
- router/provider 目录扁平化(app/meeting/router.go / app/meeting/provider.go)
- 延续项目 Go 侧"零 _test.go"风格,用代码审查 + psql 真库验证 + Playwright E2E 三层守护
文档同步:
- docs/progress/CURRENT_STATUS.md 新增 Task 3 / Task 4 交付段落
- .cursor/rules/project-context.mdc Phase 2e-2 进度推进至 Task 0-4 ✅
- docs/plans/2026-04-21-phase2e-2-implementation.plan.md Task 3 / Task 4 标记完成 + 实际产出 vs 计划差异
Made-with: Cursor
|
2026-04-21 16:04:57 +08:00 |
|
bujinyuan
|
f1853f125d
|
feat: Phase 2e-1 统一通知中心 + 我的 TabBar 聚合未读红点
后端(notify 模块)
- 新增 notify 模块:DAO/Service/Pusher 接口/Controller/Router/CleanupTask
- 数据库 DDL:notify_notifications 表 + 3 索引(user+created/user+is_read/user+category)
- 11 种 type 枚举(好友/群聊 9 种 + meeting_* 2 种预留)+ 4 种 category
- 跨模块集成:contact 3 处 Pusher(friend_request/accepted/rejected)
- 跨模块集成:group 6 处 Pusher(invite/join_request/approved/rejected/kicked/role_changed)
- WS handler 断线补偿:连接建立即推送 notify.unread.total
- 5 REST API(4 用户 + 1 管理员广播)+ 2 WS 事件(notify.new / notify.unread.total)
- 30 天已读通知定时清理(未读永久保留)
- Provider/Wire 依赖注入(NotifyPusher、NotifyConnectHook、UserInfoResolver 接口)
前端
- 新增 notify 模块:API/Pinia Store(5 分类分页缓存 + 未读数 + WS 事件)/NotifyItem/通知中心主页
- profile 入口:铃铛 badge + 菜单项 badge + 数字显示
- App.vue/login 初始化 notifyStore WS 监听;logout 调用 notifyStore.reset() 清缓存
- 清理 contact.js/group.js 中散落 toast 与冗余 notify.friend.request/group.join.request 处理
- CustomTabBar 新增 hasDot() 聚合指示器:我的 Tab 显示纯红点(无数字),
当前聚合 notifyStore.unreadTotal,未来可扩展「资料待完善/安全提醒/新版本」等
文档
- 新增 Phase 2e 整体路线图 docs/plans/2026-04-20-phase2e-design.md
- 新增 Phase 2e-1 专用设计 docs/plans/2026-04-20-phase2e-1-design.md(§6.4 TabBar 聚合红点)
- 新增 Phase 2e-1 实施计划 docs/plans/2026-04-20-phase2e-1-implementation.plan.md
- 新增 E2E 验证报告 test-report-phase2e-1-notification.md(含 Playwright MCP 2 个现场 Bug 修复记录)
- 更新 docs/progress/CURRENT_STATUS.md、docs/api/README.md、docs/api/frontend/notify.md
- 更新 .cursor/rules/project-context.mdc、docs/plans/2026-02-27-echochat-system-design.md
其他
- .gitignore 排除 .playwright-mcp/ MCP 临时快照
架构决策
- 单端 WS 连接:沿用现有 ws.Hub,多端已读同步推迟到 Phase 2f/二期
- 跨模块依赖:contact/group → notify 严格单向(接口注入模式)
- 降级策略:Pusher 先入库后推送;WS 失败不回滚入库;入库失败仅 Warn 不影响业务
Playwright MCP 回归(4 类场景全通)
- 实时推送(admin 广播 → 1s 内前端自动插入 + 角标 +1)
- Deep-link 跳转(好友申请通知 → contact/request 页)
- 批量清零(全部已读按钮)
- TabBar 聚合红点(有未读亮/全部已读灭)与 notifyStore.unreadTotal 三层同步
Made-with: Cursor
|
2026-04-21 10:21:01 +08:00 |
|
bujinyuan
|
ccfceefdaf
|
feat:聊天页面相关功能优化,提供用户体验感
|
2026-04-20 15:40:16 +08:00 |
|
bujinyuan
|
0c1540bdee
|
feat:聊天信息支持 文件、图片、语音发送,增加一键启停脚本
|
2026-04-20 11:53:27 +08:00 |
|
bujinyuan
|
8ee870636c
|
feat:群聊问题修复+相关项目文档更新
|
2026-03-05 09:24:49 +08:00 |
|
bujinyuan
|
19979da59e
|
feat(phase2c): 群聊与已读回执功能完整实现
Phase 2c 全部 14 个 Task 完成,包含:
后端(Go):
- MinIO 文件存储服务集成(Docker + Go SDK + 通用上传 API)
- Group 模块完整实现(DAO + Service + Controller + Router + Wire)
- 18 个群管理 REST API + 11 个 WS 群事件推送
- 群创建/解散/邀请/踢人/退出/转让群主/设管理员/禁言/全体禁言/群公告/群昵称/免打扰/搜索
- IM Service 扩展(群消息发送/撤回 + @提醒 + 管理员无时限撤回)
- 已读回执后端(单聊会话级 last_read_msg_id + 群聊消息级 im_message_reads)
- 管理端群组管理(列表/详情/解散)
- 数据库迁移(3 张新表 + 2 张表字段扩展)
前端(uni-app):
- 群聊 Store + API 封装 + 11 个 WS 事件监听
- 已读回执 UI(单聊已读/未读标记 + 群聊 X人已读 + 已读详情页)
- 7 个群聊页面(对话/创建/设置/成员/邀请/审批/搜索)
- 会话列表改造(全部/单聊/群聊 Tab + @标记 + 免打扰标识)
管理端(Vue 3 + Element Plus):
- 群组列表页(搜索/分页/详情弹窗/解散群聊)
- 侧边栏群组管理入口
文档同步:进度/架构/设计/API/规范文档全部更新
Made-with: Cursor
|
2026-03-04 14:58:23 +08:00 |
|
bujinyuan
|
9399f86a19
|
feat:单聊页面bug修复+后台管理端好友页面bug修复+项目进度、记忆文件更新
|
2026-03-04 10:03:16 +08:00 |
|
bujinyuan
|
2c7be494f2
|
feat(im): Task 5 - IM REST Controller + Router + Wire 集成
IMController (REST API):
- GET /api/v1/im/conversations: 会话列表
- GET /api/v1/im/messages: 历史消息(游标分页)
- PUT /api/v1/im/conversations/:id/pin: 置顶/取消
- DELETE /api/v1/im/conversations/🆔 删除会话
- DELETE /api/v1/im/conversations/:id/messages: 清空记录
- GET /api/v1/im/messages/search: 全局搜索
- GET /api/v1/im/unread: 全局未读数
Wire 集成:
- IMSet Provider Set + wire.Bind 接口注入
- App struct 新增 IM 字段
- wire_gen.go 手动更新
- OfflinePusher 通过 SetOfflinePusher 注入 WS Handler
Made-with: Cursor
|
2026-03-03 10:51:56 +08:00 |
|
bujinyuan
|
1e0c061e9d
|
feat(im): Task 4 - WS 事件处理器 + 离线消息推送
EventHandler:
- im.message.send: 发送消息(解析→业务→ACK+推送)
- im.message.recall: 撤回消息
- im.conversation.read: 标记已读
- im.typing: 正在输入通知(转发对方)
- 所有事件通过 Hub.RegisterEvent 注册到路由表
OfflinePusher:
- PushOfflineMessages: 推送未读会话摘要 + 全局未读总数
- 通过 OfflineMessagePusher 接口注入 WS Handler
- WebSocket 连接建立后自动触发离线推送
Made-with: Cursor
|
2026-03-03 10:48:36 +08:00 |
|
bujinyuan
|
334d3d860b
|
feat(im): Task 3 - IM Service 核心业务 + DTO + 接口定义
IMService 核心方法:
- SendMessage: 发送消息(好友校验→查找/创建会话→幂等去重→写入→推送)
- RecallMessage: 2分钟撤回
- GetConversationList: 会话列表(含对方用户信息)
- GetHistoryMessages: 游标分页历史消息
- MarkRead / PinConversation / DeleteConversation / ClearHistory
- SearchMessages: 全局消息搜索
- GetTotalUnread: Redis 全局未读总数
DTO:
- SendMessageRequest / RecallMessageRequest
- ConversationDTO / HistoryMessageResponse
- SearchMessageRequest / MarkReadRequest / TypingRequest
接口:
- FriendChecker: 好友校验(contact 模块注入)
- UserInfoGetter: 用户信息批量查询(contact 模块注入)
Made-with: Cursor
|
2026-03-03 10:46:57 +08:00 |
|
bujinyuan
|
e091fbccb3
|
feat(im): Task 2 - IM DAO 层(会话 + 消息)
ConversationDAO:
- FindPrivateConversation: 单聊会话去重查询
- CreateWithMembers: 事务创建会话+成员
- GetUserConversations: 会话列表(含未读/置顶)
- UpdateLastMessage / IncrementUnread / ClearUnread
- SoftDeleteMember / RestoreMember / UpdateMemberPinned
- GetUnreadConversations: 离线消息推送用
MessageDAO:
- Create / GetByID / GetByConversation(游标分页)
- UpdateStatus(撤回) / DeleteByConversation(清空)
- SearchMessages(全局搜索,JOIN 权限校验)
- FindByClientMsgID(幂等去重)
Made-with: Cursor
|
2026-03-03 10:44:34 +08:00 |
|
bujinyuan
|
c23b9087b8
|
feat(ws): Task 1 - Hub 事件路由表机制
- Hub 新增 eventHandlers map + RegisterEvent / DispatchEvent 方法
- handler.go onMessage 优先查路由表,未命中走内置 fallback
- default 分支改为返回"未知事件"错误响应 + 警告日志
Made-with: Cursor
|
2026-03-03 10:43:01 +08:00 |
|
bujinyuan
|
6ab04fb902
|
feat(im): Task 0 - IM 模型定义 + 数据库表迁移 + 常量定义
- 新增 3 个 GORM 模型:Conversation / ConversationMember / Message
- 新增 IM 常量:会话类型、消息类型、消息状态、撤回时限
- main.go 添加 IM 表 AutoMigrate
- init.sql 追加 IM 模块 DDL(含索引和全文搜索 GIN 索引)
Made-with: Cursor
|
2026-03-03 10:41:42 +08:00 |
|
bujinyuan
|
c8ae70ef97
|
fix(phase2a): handleError 增强 + 代码格式化 + 测试报告归档
- auth/contact Controller handleError 增加 fallbackMsg 可变参数,未知错误可返回更有语义的降级提示
- import 排序、变量对齐等 gofmt 格式规范化
- 新增管理端测试报告和路由验证报告
Made-with: Cursor
|
2026-03-03 09:51:43 +08:00 |
|
bujinyuan
|
2c59500e27
|
fix(phase2a): 代码审查修复 - 8项关键/重要问题
安全修复:
- WebSocket Token 增加 Redis 有效性校验(已登出用户无法建立 WS)
功能修复:
- GetRecommendFriends 改为批量查询,正确返回用户名/昵称/头像
- 上下线通知:OnlineService 通过接口注入获取好友列表推送状态变更
- 管理端在线用户 API 补充用户名信息
代码质量:
- 所有 json.Marshal/Redis 错误增加检查与日志
- ContactController 13 个 endpoint 统一走 handleError 业务错误映射
- 管理端 Controller 补全包注释、函数注释和结构化日志
- 前端 5 个联系人页面 avatar 工具函数抽取到 utils/avatar.js
Made-with: Cursor
|
2026-03-02 18:48:28 +08:00 |
|
bujinyuan
|
a77669ee99
|
feat(admin): 管理端在线监控 + 好友关系管理后端
- admin/service/online_service.go: 在线用户列表/计数
- admin/controller/online_controller.go: GET /admin/online/users|count
- admin/service/contact_manage_service.go: 好友关系分页查询/管理员删除
- admin/controller/contact_manage_controller.go: GET|DELETE /admin/contacts
- 更新 admin router/provider/wire 集成新控制器
Made-with: Cursor
|
2026-03-02 17:13:06 +08:00 |
|
bujinyuan
|
1c87a466a1
|
feat(ws): 在线状态管理(Redis SET + TTL 心跳续期)
- app/ws/online_service.go: 上线/下线/心跳续期/批量查询在线状态
- 集成到 WebSocket handler: 连接时写入 Redis, 断线时清除
- client.go: 添加 DisconnectHandler 回调
- Redis 键: echo:user:online (SET) + echo:user:status:{uid} (TTL 60s)
Made-with: Cursor
|
2026-03-02 17:10:13 +08:00 |
|
bujinyuan
|
632e3b9a28
|
feat(contact): Controller、Router 与 Wire 集成
- controller/contact_controller.go: 全部 17 个 REST API 端点处理器
- router.go: Contact 模块路由注册(JWT 中间件保护)
- provider.go: Wire Provider Set(DAO + Service + Controller)
- 更新全局 provider、wire.go、router.go 集成 Contact 模块
Made-with: Cursor
|
2026-03-02 17:07:41 +08:00 |
|
bujinyuan
|
978037f085
|
feat(contact): Contact Service 业务逻辑
- 好友申请:发送/接受/拒绝 + 前置校验(自加/已好友/重复申请/黑名单)
- 好友管理:删除好友/更新备注
- 黑名单:拉黑(同时解除好友)/取消拉黑/黑名单列表
- 搜索:用户搜索(含好友标识)/好友推荐(基于共同好友)
- 分组:CRUD + 移动好友到分组
- 实时通知:好友申请/接受通过 Redis Pub/Sub 推送
Made-with: Cursor
|
2026-03-02 17:04:30 +08:00 |
|
bujinyuan
|
d4ab5af34e
|
feat(contact): Contact 模型、DAO、常量与 DTO
- model/friendship.go: 好友关系模型(双向存储,4 种状态)
- model/friend_group.go: 好友分组模型
- constants/contact.go: 好友关系状态常量
- dto/contact_dto.go: 联系人请求/响应 DTO
- dao/friendship_dao.go: 好友关系 CRUD + 搜索 + 共同好友
- dao/friend_group_dao.go: 好友分组 CRUD + 移动好友
Made-with: Cursor
|
2026-03-02 17:03:13 +08:00 |
|
bujinyuan
|
bfb4fb0ccb
|
feat(ws): WebSocket 核心模块(Hub + Client + PubSub + Handler)
- pkg/ws/message.go: 统一消息协议(Message/Response/PushMessage)
- pkg/ws/hub.go: Hub 连接管理(注册/注销/按 userID 查找/在线计数)
- pkg/ws/client.go: 客户端连接封装(readPump/writePump/心跳 30s)
- pkg/ws/pubsub.go: Redis Pub/Sub 消息路由(按用户频道发布/订阅)
- app/ws/handler.go: WebSocket 升级处理(JWT 认证 + 消息分发)
- app/ws/router.go: GET /ws 路由注册
- app/ws/provider.go: Wire Provider Set
- 更新 provider/router 集成 WebSocket 模块
Made-with: Cursor
|
2026-03-02 16:46:17 +08:00 |
|
bujinyuan
|
fa6f1e5c58
|
feat: 角色等级体系与权限管控实施
- 数据库:auth_roles 表新增 level 字段(1=超管, 10=管理员, 100=普通用户)
- 后端:新增 GetAllRoles/GetUserMaxLevel/SetUserRoles/FindByCodeList DAO 方法
- 后端:SetRolesRequest 替换 AssignRoleRequest,AdminUserInfo.Roles 改为 []RoleInfo
- 后端:所有管理操作(禁用/启用/角色分配/创建用户)强制层级权限校验
- 后端:PUT /users/:id/roles(批量设置角色)+ GET /roles(角色列表)
- 前端:角色管理改为 Checkbox Group 多选,高等级角色禁用
- 前端:禁用/启用按钮受角色层级约束,列表页操作按钮权限管控
- 前端:创建用户对话框角色选项根据操作者等级动态过滤
- 文档:API 文档、设计方案、集成规范、进度文档同步更新
Made-with: Cursor
|
2026-03-02 15:40:02 +08:00 |
|
bujinyuan
|
13c6b44352
|
fix: 管理端所有认证接口统一使用 /api/v1/admin/auth/* 路由
后端:
- 新增管理端认证路由组 /api/v1/admin/auth/(JWT + admin 角色双重检查)
- 管理端登出:POST /api/v1/admin/auth/logout
- 管理端获取个人信息:GET /api/v1/admin/auth/profile
- 管理端更新个人信息:PUT /api/v1/admin/auth/profile
- 管理端修改密码:PUT /api/v1/admin/auth/password
前端:
- admin/src/api/auth.js 所有接口全部改为 /api/v1/admin/auth/*
- 登出和获取个人信息不再使用前台的 /api/v1/auth/ 路由
Made-with: Cursor
|
2026-03-02 14:33:18 +08:00 |
|
bujinyuan
|
c3e8600b24
|
fix: 前后台 Token Redis 存储隔离,修复同账号互相覆盖问题
核心变更:
- Redis key 加入 clientType 前缀:echo:auth:token:{frontend|admin}:{user_id}
- JWT Claims 新增 client_type 字段区分前台/管理端
- 新增 constants/client_type.go 定义 ClientTypeFrontend / ClientTypeAdmin
- 全链路传递 clientType:Controller → Service → TokenStore → Redis
- 中间件从 JWT Claims 提取 clientType 做 Redis 校验
- 登出只删除当前端 Token,不影响另一端
前端变更:
- 管理端 login API 改为调用 POST /api/v1/admin/auth/login(之前错误调用了前台接口)
文档更新:
- 系统设计文档、实施计划、API文档、开发规范、项目进度全部同步
Made-with: Cursor
|
2026-03-02 14:28:45 +08:00 |
|
bujinyuan
|
e1348f57f2
|
fix: 统一前后端错误提示处理,修复3个问题
1. 管理端 request.js: 所有401均优先显示后端实际message,
非登录页才清除Token并跳转
2. 前台用户端 request.js: 区分登录/注册请求与已认证请求,
登录失败时只显示后端message,不清Token不跳转
3. 后端 auth_service: 登录时用户不存在统一返回"账号或密码错误"
(防止用户枚举攻击,不再返回404"用户不存在")
Made-with: Cursor
|
2026-03-02 14:05:03 +08:00 |
|
bujinyuan
|
4d03215fe4
|
feat: Phase 1 完成 — 基础设施 + 用户认证 + 管理端 + 端到端验证
Phase 1 (基础设施与用户认证) 全部 11 个 Task 开发完成:
后端 (Go):
- Auth 模块: 注册/登录/JWT(有状态)/Profile/密码修改
- Admin 模块: 用户列表/详情/禁用/启用/角色分配/创建用户
- 中间件: JWT认证 + RBAC角色权限 + 请求日志 + CORS + Panic恢复
- Dockerfile 多阶段构建 + Docker Compose 全栈部署
前台 (uni-app):
- 登录/注册页面 + 自定义 TabBar + 个人中心
- 请求封装 + 状态管理 (Pinia)
管理端 (Vue 3 + Element Plus):
- 登录/仪表盘/用户列表/用户详情
- Axios 封装 + 路由守卫 + Pinia 状态管理
验证:
- 全流程 API 端到端测试通过
- Playwright 页面自动化验证通过
- code-reviewer 代码审查通过
Made-with: Cursor
|
2026-03-02 11:31:24 +08:00 |
|
bujinyuan
|
e9bd4dd204
|
fix: 时间精度精确到秒 + 同步全部文档到最新状态
时间字段修正:
- init.sql: 所有 TIMESTAMP 改为 TIMESTAMP(0),精确到秒
- GORM 模型: 所有时间字段添加 type:timestamp(0) tag
- 已有数据库表通过 ALTER TABLE 修正列类型
文档同步(架构设计 + 实施步骤):
- system-architecture.md:
- auth 模块描述更新为"有状态 JWT Token 管理(Redis 存储)"
- 开发环境端口 8080 → 8085
- phase1-foundation-and-auth.md:
- Go 版本 1.22+ → 1.23+
- 常量命名更新为驼峰风格(UserStatusActive / RoleUser 等)
- Task 4 完整重写:增加 token_store.go、TokenValidator 接口、有状态 JWT
- Task 5 端口号 8080 → 8085,测试命令增加登出失效验证
- 依赖版本选择原则说明
Made-with: Cursor
|
2026-02-28 17:04:47 +08:00 |
|
bujinyuan
|
b607434c57
|
fix(auth): 有状态 JWT + 统一响应格式,严格遵循设计方案
1. 有状态 JWT(Token 存 Redis):
- 新增 token_store.go: Token 的 Redis 存取管理
- echo:auth:token:{user_id} → Access Token (TTL = access_expire_min)
- echo:auth:refresh:{user_id} → Refresh Token (TTL = refresh_expire_day)
- 登录/注册时自动将 Token 存入 Redis(覆盖旧 Token,实现单设备登录)
- JWT 中间件增加 Redis 有效性校验(TokenValidator 接口解耦)
- 登出时从 Redis 删除 Token,使其立即失效
- 刷新 Token 时校验 Redis 中的 Refresh Token
2. 统一成功响应为 "success" + 200:
- 注册接口改用 ResponseOK(原 ResponseCreated/201)
- 所有成功响应统一为 {"code": 0, "message": "success"}
3. API 文档同步更新:
- frontend/auth.md: 登出说明改为 Redis 方案、注册响应统一
- README.md: 移除 "created" 示例
已验证:登出后 Token 立即失效 ✓ 重新登录后新 Token 有效 ✓
Made-with: Cursor
|
2026-02-28 16:57:46 +08:00 |
|
bujinyuan
|
5a65716d10
|
docs(api): 同步 API 文档与实际实现一致
README.md:
- 开发环境端口 8080 → 8085
- 统一响应格式添加 trace_id 字段
- 成功消息 "ok" → "success",创建 "created"
frontend/auth.md(全面更新):
- 注册响应:201 状态码 + message="created" + expires_in=7200
- 所有响应示例:添加 trace_id 和 time 字段
- user 对象:添加 gender 字段
- 退出登录:更新为无状态 JWT 说明(非 Redis)
- 刷新 Token:添加 user 字段到响应
- profile:添加 phone + created_at 字段
- 错误码:统一使用 HTTP 状态码说明表
代码同步:
- dto.UserInfo: 添加 Phone + CreatedAt 字段
- auth_service.buildUserInfo: 填充新字段
Made-with: Cursor
|
2026-02-28 16:48:17 +08:00 |
|
bujinyuan
|
d975adaf2a
|
feat(auth): 完整认证系统 — 注册/登录/JWT/路由(Task 4 + Task 5)
Task 4 — 认证服务层:
- pkg/utils/password.go: bcrypt 密码加密与校验
- pkg/utils/jwt.go: Access/Refresh Token 生成与解析(jwt/v5@v5.2.1,兼容 Go 1.23)
- app/dto/auth_dto.go: 认证相关请求/响应 DTO(含参数校验 binding tag)
- app/auth/service/auth_service.go: 核心业务逻辑(注册、登录、管理员登录、Token 刷新、个人信息、改密码)
- pkg/middleware/auth.go: JWT 认证中间件 + 角色权限检查中间件
Task 5 — Controller 与路由注册:
- app/auth/controller/auth_controller.go: 前台认证接口(7 个 API)
- app/auth/controller/admin_auth_controller.go: 后台管理认证接口
- app/auth/router.go: auth 模块路由定义(模块自包含)
- router/router.go: 主路由汇总入口(仅做调度,不含具体路由定义)
- cmd/server/main.go: 路由注册迁移到 router.Setup()
已验证全部接口:注册 ✓ 登录 ✓ 获取 profile ✓ 错误密码 ✓ 未认证拒绝 ✓ 非管理员拒绝 ✓
Made-with: Cursor
|
2026-02-28 16:42:28 +08:00 |
|
bujinyuan
|
4d3d486902
|
refactor(middleware): 精简请求日志 — 采用社区标准分层策略
- 移除 Request Body 记录(交由 Controller 层以结构化参数形式记录)
- 移除正常响应 Body 的 DEBUG 记录(减少日志量)
- 保留 HTTP 元信息:method/path/handler/status/latency/ip/query
- 保留错误响应(4xx/5xx)的 Response Body 记录
- 导出 IsSensitivePath 供 Controller 层调用
- 重写架构文档 8.6 节:分层日志架构表、字段说明、分级策略
- 更新 phase1 实施计划中间件描述
Made-with: Cursor
|
2026-02-28 16:10:07 +08:00 |
|
bujinyuan
|
a6ef49a3e0
|
feat(middleware): 请求日志新增 handler 字段定位实际处理函数
- 通过 c.HandlerName() 获取处理请求的 handler 函数名
- 解决 caller 始终指向中间件文件无法定位业务代码的问题
- 同步更新架构文档日志示例,补充 caller/handler 说明
Made-with: Cursor
|
2026-02-28 15:56:32 +08:00 |
|
bujinyuan
|
8a023dfd87
|
feat(middleware): 请求日志增强 — 记录请求参数 + 响应数据
- Query 参数:INFO 级别始终记录(所有环境生效)
- Request Body:INFO 级别始终记录(所有请求方式)
- 文件上传自动跳过,仅标记 [file upload]
- 敏感路径(登录/注册/改密码)自动脱敏 password 字段
- Body 超过 4KB 自动截断
- Response Body:DEBUG 级别记录正常响应,4xx/5xx 错误在 INFO 也记录
- 响应 Body 最大记录 2KB
- 状态码分级:5xx→ERROR / 4xx→WARN / 慢请求→WARN / 正常→INFO
Made-with: Cursor
|
2026-02-28 15:49:19 +08:00 |
|
bujinyuan
|
028cca8695
|
docs(config): 配置文件添加完整中文注释
Made-with: Cursor
|
2026-02-28 15:23:52 +08:00 |
|
bujinyuan
|
63c6079667
|
feat(logs): 日志系统升级 — 文件轮转 + 分级存储
- 引入 lumberjack 实现日志文件自动轮转(按大小切割、保留数量、过期清理)
- app.log: 全量日志(JSON 格式),便于后期接入 ELK/Loki
- error.log: 仅 WARN 及以上级别,便于快速定位问题
- 控制台输出保持不变(彩色可读文本)
- 配置新增 log.file 节,支持 enable/dir/max_size/max_backups/max_age/compress
Made-with: Cursor
|
2026-02-28 15:15:00 +08:00 |
|
bujinyuan
|
8a6576a2f7
|
feat(auth): 用户/角色模型与数据访问层
- constants: 用户状态、性别、角色代码常量定义
- model: User/Role/UserRole GORM 模型
- dao: UserDAO (CRUD + 账号查询) + RoleDAO (角色分配/查询/检查)
- provider: Auth 模块 Wire Provider Set
Made-with: Cursor
|
2026-02-28 10:42:34 +08:00 |
|
bujinyuan
|
c8ffbedf75
|
feat(backend): Go 服务骨架(配置、日志、数据库、中间件、Wire)
- config: Viper YAML 配置 + 环境变量覆盖
- logs: zap 结构化日志 + trace_id 链路追踪 + 敏感信息脱敏
- db: PostgreSQL (GORM) + Redis (go-redis) 连接管理
- middleware: Trace/Logger/CORS/Recovery 四层中间件
- provider: Wire 编译时依赖注入
- main.go: 优雅启动/关闭 HTTP 服务
Made-with: Cursor
|
2026-02-28 10:41:20 +08:00 |
|
bujinyuan
|
3070acda40
|
feat:大型音视频会议直播系统--项目代码初始化
|
2026-02-27 14:39:03 +08:00 |
|