6.4 KiB
6.4 KiB
AGENTS.md
Non-negotiables
- 任何开发,不需要历史兼容,目前只是在开发阶段
- 写代码不要猜。先读当前实现、接口、配置和测试,再改。
- 不写流水账。文档、注释和总结都要解释边界、决策和可执行动作。
- 前端或客户端改动不要添加无意义描述文案。界面文字必须服务真实操作或状态。
- 不把房间核心状态扩散到多个服务。Room Cell 仍然是房间状态 owner。
- 不把连接态塞进
room-service。客户端长连接和消息投递属于腾讯云 IM。 - 代码永远保持高密度注释
- 写代码的时候碰到为提交修改不用关心,只去做自己的
Architecture Boundaries
gateway-service只做 HTTP 入口、鉴权、协议转换、腾讯云 IM UserSig 签发和内部 gRPC 编排。room-service负责 Room Cell、房间状态、麦位、房间 presence、本地榜、snapshot、command log、outbox、Redis lease,以及腾讯云 IM 群组/房间系统消息桥接。- 腾讯云 IM 负责客户端长连接、房间群消息、公屏、单聊、离线/漫游和全球接入;
wallet-service负责账务语义。SendGift必须先扣费成功,再落房间表现。activity-service通过 room outbox 事件消费,不侵入 Room Cell 主链路。user-service负责用户主数据,不应该成为房间高频流程的同步中心。cron-service只负责后台调度、任务运行记录和通过内部 gRPC 触发 owner service 批处理;不能直接拥有房间、账务、用户或活动业务状态。server/admin是后台管理服务独立 module,负责管理员、RBAC、菜单、审计和后台 HTTP API;访问 app 后端只能通过hyapp.local/api生成的 protobuf client 或明确的集成接口。api是独立 Go module,module path 为hyapp.local/api,只放 protobuf contract 和生成代码,不放服务实现或业务工具包。
Persistence Rules
room-service生产路径使用 MySQL repository 和 Redis directory。memoryrepository/directory 只用于单元测试或明确的本地隔离测试。- MySQL 是房间恢复的持久来源:
rooms、room_snapshots、room_command_log、room_outbox。 - Redis 只保存当前路由/lease 等热状态,不能作为唯一恢复来源。
- Redis lease 更新必须保持原子性,不能改回非原子的 GET + SET 接管逻辑。
Time Rules
- 全局业务时间统一使用 UTC,不使用服务器所在地、容器本地时区、客户端时区或 IP 推断时区作为结算、统计、刷新和幂等周期的切日来源。
- 跨服务契约、HTTP 响应、数据库业务事实和 outbox payload 中的时间统一使用 Unix epoch milliseconds,字段名保持
*_ms。 - 统计、账务和列表时间范围统一使用
[start_ms, end_ms):包含开始毫秒,不包含结束毫秒,避免相邻区间重复计算边界记录。 - 每日任务、自然日刷新和
task_day统一按 UTC 日期计算;不要重新引入task_timezone、time.Local或loc=Local。 - MySQL DSN 必须使用
loc=UTC;Docker/Compose 服务必须保持TZ=UTC,MySQL 必须保持--default-time-zone=+00:00。 - 如果产品需要用户本地时间展示,只能在展示层或资料/风控元数据中处理;要把它用于业务切日,必须先形成明确产品规则、契约字段和边界测试。
Protocol Rules
- 外部 HTTP JSON 入口在
gateway-service。 gateway-service的/api/v1业务响应必须使用{code,message,request_id,data}envelope;healthcheck 不套业务响应格式。request_id是后端生成的链路追踪字段,必须透传到内部 gRPCRequestMeta.request_id;不要把它当幂等键使用。- 外部实时消息入口在腾讯云 IM SDK;本仓库只提供
/api/v1/im/usersig签发登录票据。 - 内部服务通信统一 gRPC + protobuf,Go 代码通过
hyapp.local/api/proto/...引用生成包。 - 当前处于开发阶段,不保留历史协议;Proto/API/DB 可以按当前事实直接调整。
- 修改
api/proto后必须运行make proto,并提交生成后的.pb.go/_grpc.pb.go。 - 不要在服务之间直接 import 对方
internal包。跨服务只走 protobuf client 或明确的接口抽象。 server/admin不能 importhyapp/services/*或hyapp/pkg/*;后台专属基础设施放在server/admin/internal/platform。
Port Rules
本项目本地端口使用 13xxx:
13000: gateway HTTP13001: room gRPC13004: wallet gRPC13005: user gRPC13006: activity gRPC13007: cron gRPC23306: local Docker MySQL host port13379: local Docker Redis host port
不要重新引入 808x 作为默认端口。
Coding Rules
- 默认使用 Go 标准库和仓库已有小包;不要为了轻量逻辑引入重框架。
- 手写代码保持高密度有效注释,注释解释工程语义和失败分支,不复述语法。
- 新增配置必须同时考虑本地
config.yaml、Dockerconfig.docker.yaml、以及线上配置示例。 - 新增服务依赖必须在
docker-compose.yml中体现本地可运行形态。 - 数据库表结构变更必须同步更新
services/room-service/deploy/mysql/initdb。 - 不要把线上密钥、云数据库密码、Redis 密码写进真实配置。只能写占位示例。
- 保持
gofmt,不要手调 Go import 顺序。
Test Expectations
改动后至少运行:
make test
涉及 protobuf 时运行:
make proto
go test ./...
涉及 Docker、端口、服务配置或基础设施时运行:
docker compose config
docker compose build
涉及启动链路时实际拉起:
docker compose up -d
docker compose ps
docker compose down
Safe Change Checklist
- 先确认改的是服务内部逻辑、跨服务契约、配置、还是部署编排。
- 跨服务字段优先改 protobuf,不要在 HTTP handler 或腾讯云 IM 自定义消息 payload 里偷偷扩字段。
- 房间状态变更必须经过 Room Cell 命令链路。
- 需要恢复的关键动作必须写 command log 或 snapshot,不能只改内存。
- 房间外副作用优先走 outbox,除非是明确的同步主链路依赖。
- 新增统计、账务、任务刷新或时间范围逻辑时,必须补 UTC 边界测试,至少覆盖开始边界、结束前一毫秒和结束边界。
- 文档只写当前事实和明确约束,不记录“做了什么”的流水账。