# Coding Conventions **Analysis Date:** 2026-03-27 ## Naming Patterns **Files:** - Go 源码使用 `snake_case.go` 或按领域拆分的普通小写命名;路由文件按模块命名放在 `internal/routes/*.go`,Handler 按域放在 `internal/handler/admin/*.go`、`internal/handler/auth/*.go`、`internal/handler/app/*.go`。 - OpenAPI 与规范文档使用明确用途命名,例如 `docs/api-documentation-guide.md`、`docs/admin-openapi.yaml`、`cmd/api/docs.go`、`cmd/gendocs/main.go`。 - 规范脚本使用动词前缀命名,例如 `scripts/check-all.sh`、`scripts/check-service-errors.sh`、`scripts/check-comment-paths.sh`、`scripts/verify_migration/main.go`。 **Functions:** - 导出函数/方法使用 Go 的 `PascalCase`,例如 `NewAccountHandler()`、`Create()`、`Success()`、`RedisOrderIdempotencyKey()`,证据见 `internal/handler/admin/account.go`、`pkg/response/response.go`、`pkg/constants/redis.go`。 - 未导出帮助函数使用 `camelCase`,例如 `generateOpenAPIDocs()`、`generateAdminDocs()`、`handleError()`、`safeLogWithLevel()`,证据见 `cmd/api/docs.go`、`cmd/gendocs/main.go`、`pkg/errors/handler.go`。 **Variables:** - 局部变量使用英文 `camelCase`,例如 `outputPath`、`httpStatus`、`roleID`、`groupPath`,证据见 `cmd/api/docs.go`、`pkg/errors/handler.go`、`internal/handler/admin/account.go`。 - 错误变量统一使用 `err`,成功返回数据常用业务名,例如 `account`、`accounts`、`roles`,证据见 `internal/handler/admin/account.go`。 **Types:** - 结构体和接口使用 `PascalCase`,接口语义化命名,配合 `-er` 后缀规则;项目规范明确要求接口名使用 `-er`,见 `AGENTS.md`。 - 路由文档元数据类型使用语义名,如 `RouteSpec`、`FileUploadField`,证据见 `internal/routes/registry.go`。 ## Code Style **Formatting:** - 使用 `gofmt`;项目在 `AGENTS.md` 明确要求“使用 gofmt 格式化”。 - 代码风格遵循 Go 惯用法,避免 Java 式过度抽象;证据见 `AGENTS.md` 的“Go 惯用法 vs Java 风格”。 **Linting / Scripted Checks:** - 仓库未检测到 `.golangci.yml`、`golangci-lint`、`eslint`、`prettier` 之类自动 lint 配置;当前质量门主要依赖 shell 脚本和人工审查。 - `scripts/check-service-errors.sh`:扫描 `internal/service/**/*.go` 中的 `fmt.Errorf`,要求改用 `errors.New()` / `errors.Wrap()`。 - `scripts/check-comment-paths.sh`:扫描 `internal/handler/` 中残留的 `/api/v1` 注释,要求改成真实路径 `/api/admin`、`/api/h5`、`/api/c/v1`。 - `scripts/check-all.sh`:串行执行以上两个检查。 - 当前仓库与脚本规则存在冲突:`internal/service/polling/alert_service.go` 仍存在 4 处 `fmt.Errorf(...)`,按 `scripts/check-service-errors.sh` 的规则属于违规现状。 ## Language & Comment Requirements **语言要求:** - 用户可见内容、日志、注释、文档、提交信息都使用中文;变量名、函数名、类型名使用英文,证据见 `AGENTS.md` 的“语言要求”。 **注释要求:** - 导出包、结构体、接口、函数、方法、常量、变量必须有中文文档注释,证据见 `AGENTS.md`。 - Handler 方法注释必须包含 HTTP 方法与真实路径;实际示例见 `internal/handler/admin/account.go`、`internal/handler/callback/payment.go`。 - 注释解释“为什么”,不要复述代码;复杂逻辑必须有实现注释,证据见 `AGENTS.md`。 - 常量必须带中文注释;实际示例见 `pkg/constants/constants.go`、`pkg/constants/redis.go`。 ## Import Organization **Order:** 1. Go 标准库,例如 `strconv`、`time`、`regexp`。 2. 第三方库,例如 `github.com/gofiber/fiber/v2`、`go.uber.org/zap`。 3. 项目内包,例如 `github.com/break/junhong_cmp_fiber/pkg/errors`、`internal/service/account`。 **Pattern:** - 多数组件按“标准库 → 项目包/第三方包”分组,并保留空行分隔,证据见 `internal/handler/admin/account.go`、`pkg/errors/handler.go`、`cmd/gendocs/main.go`。 - 项目使用完整 module import path,未体现短别名路径;必要时用语义别名,例如 `apphandler`、`accountService`,证据见 `cmd/gendocs/main.go`、`internal/handler/admin/account.go`。 **Path Aliases:** - 未检测到 TS/JS 式路径别名;Go 代码通过 module path `github.com/break/junhong_cmp_fiber/...` 引用。 ## Layering Rules **Required Architecture:** - 必须遵循 `Handler → Service → Store → Model`,证据见 `AGENTS.md` 与 `README.md`。 **How to apply it:** - Handler 只做参数解析、上下文读取、调用 service、返回统一响应;示例见 `internal/handler/admin/account.go`。 - Service 承载业务逻辑,并向下调用 Store;项目规范在 `AGENTS.md` 明确禁止在 Handler 中写业务逻辑。 - Store 负责数据访问和事务;规范说明见 `AGENTS.md`、`README.md`。 - Model/DTO 定义请求、响应和持久化结构;OpenAPI 文档也依赖 DTO 元数据,证据见 `docs/api-documentation-guide.md`。 ## Error Handling **Centralized package:** - 所有错误码与应用错误类型集中在 `pkg/errors/`,证据见 `pkg/errors/codes.go`、`pkg/errors/errors.go`、`pkg/errors/handler.go`、`AGENTS.md`。 **Rules to follow:** - Handler 层不要把底层错误直接暴露给客户端;参数校验失败统一返回 `errors.New(errors.CodeInvalidParam)` 或其中文变体,证据见 `AGENTS.md`、`internal/handler/admin/account.go`。 - Service 层对外不要返回 `fmt.Errorf(...)`,要返回 `errors.New(...)` 或 `errors.Wrap(...)`;脚本 `scripts/check-service-errors.sh` 专门检查这一点。 - 全局错误处理使用 `pkg/errors/handler.go` 的 `SafeErrorHandler()` / `handleError()`,统一输出 `{code, data, msg, timestamp}`,并按错误码映射 HTTP 状态码与日志级别。 - 5xx 响应统一走通用中文消息,避免泄露敏感信息,证据见 `pkg/errors/handler.go`。 **Error code system:** - `pkg/errors/codes.go` 定义 1000-1999 客户端错误、2000-2999 服务端错误。 - `pkg/errors/codes.go` 在 `init()` 校验全部错误码都必须映射消息,新增错误码时要同步维护 `allErrorCodes` 和 `errorMessages`。 ## Response Format **Envelope:** - 所有 API 成功响应统一使用 `pkg/response/response.go`:`{code, data, msg, timestamp}`。 - `Success()` 返回 `msg: "success"`;`SuccessWithMessage()` 允许覆盖消息;`SuccessWithPagination()` 将分页数据包进 `PaginationData`。 **How handlers should respond:** - Handler 成功路径直接调用 `response.Success()` / `response.SuccessWithPagination()`;实际示例见 `internal/handler/admin/account.go`、`internal/handler/admin/iot_card.go`、`internal/handler/admin/shop.go`。 - 错误路径直接 `return err` 交给全局 ErrorHandler,不在 Handler 内手动拼接 JSON,证据见 `internal/handler/admin/account.go`、`pkg/errors/handler.go`。 ## Constant Management **Location:** - 所有常量统一放在 `pkg/constants/`,证据见 `AGENTS.md` 与 `pkg/constants/constants.go`、`pkg/constants/redis.go`。 **Rules to follow:** - 禁止硬编码字符串与 magic numbers;公共业务值放进 `pkg/constants/constants.go`。 - Redis Key 必须通过函数生成,而不是手写字符串,命名格式使用 `Redis{Module}{Purpose}Key(...)`,证据见 `pkg/constants/redis.go` 与 `AGENTS.md`。 - 常量要配中文注释;`pkg/constants/constants.go` 中的用户类型、任务类型、分页上限、默认管理员信息都按此方式组织。 ## API / OpenAPI Conventions **Route registration:** - 所有 HTTP 路由都应在 `internal/routes/*.go` 中通过 `Register()` 注册,不要直接 `router.Get/Post/...`,证据见 `docs/api-documentation-guide.md`、`internal/routes/registry.go`。 - `Register()` 同时负责 Fiber 路由注册和 OpenAPI 生成;当 `doc != nil` 时,会把 `/:id` 转为 OpenAPI 的 `/{id}`,证据见 `internal/routes/registry.go`。 **RouteSpec requirements:** - 每个接口需要提供中文 `Summary`,可选 Markdown `Description`,并声明 `Input`、`Output`、`Tags`、`Auth`;证据见 `internal/routes/registry.go`、`docs/api-documentation-guide.md`。 - DTO 字段必须使用 `description` 标签,不依赖行尾注释;枚举字段要在 `description` 中列出可选值,证据见 `docs/api-documentation-guide.md`。 **Handler + docs generator sync:** - 新增 Handler 时,除业务接线外,还必须同步更新 `internal/bootstrap/types.go`、`internal/bootstrap/handlers.go`、`internal/routes/admin.go`、`cmd/api/docs.go`、`cmd/gendocs/main.go`,证据见 `docs/api-documentation-guide.md` 与 `AGENTS.md`。 - 文档生成命令使用 `go run cmd/gendocs/main.go` 或 `make docs`;代码证据见 `cmd/gendocs/main.go`、`Makefile`。 ## Documentation Expectations **Required docs workflow:** - 每个功能应在 `docs/{feature-id}/` 创建总结文档,并同步更新 `README.md`,证据见 `AGENTS.md`。 - 文档和说明统一使用中文。 - API 文档规范集中在 `docs/api-documentation-guide.md`;开发总规范集中在 `AGENTS.md`。 **Repository reality:** - `README.md` 仍保留旧的自动化测试与覆盖率章节、旧项目结构中的 `tests/` 目录描述、以及“CI/CD 自动执行检查”的表述。 - 当前仓库未发现任何 `*_test.go` 文件,也未发现 `tests/` 目录内容;因此后续文档和执行应优先遵循 `AGENTS.md` 的现行规则,而不是 `README.md` 中这些过期段落。 ## Operational Scripts **Quality / convention scripts:** - `bash scripts/check-service-errors.sh`:检查 Service 层是否违规使用 `fmt.Errorf`。 - `bash scripts/check-comment-paths.sh`:检查 Handler 注释路径是否残留 `/api/v1`。 - `bash scripts/check-all.sh`:运行上述两个检查。 **Documentation script:** - `make docs` → `go run cmd/gendocs/main.go`,用于生成 `docs/admin-openapi.yaml`,证据见 `Makefile`、`cmd/gendocs/main.go`。 **Migration verification helper:** - `go run scripts/verify_migration/main.go`:这是一个面向数据库迁移结果的人工验证脚本,会直接连接数据库并查询字段,不是自动测试框架,证据见 `scripts/verify_migration/main.go`。 **Caution:** - `Makefile` 的 `test` 目标仍定义为 `go test -v ./...`,但这反映的是旧工具入口,不代表当前团队允许自动化测试。 ## Module Design **Exports:** - 构造函数使用 `NewXxx...`,例如 `NewAccountHandler()`、`NewGenerator()`。 - Handler、response、errors、constants 都以小包单职责方式导出少量明确入口,证据见 `internal/handler/admin/account.go`、`pkg/response/response.go`、`pkg/errors/errors.go`。 **Barrel Files:** - 未检测到 JS/TS 式 barrel file;Go 通过包目录与导出符号组织模块。 ## Prescriptive Summary - 写新 Handler 时:在 `internal/handler/...` 保持中文注释 + 英文标识符,只解析请求并调用 Service,成功统一走 `pkg/response/response.go`,失败直接返回 `error`。 - 写新业务错误时:先在 `pkg/errors/codes.go` 注册错误码与中文消息,再用 `errors.New()` / `errors.Wrap()`。 - 写新常量或 Redis Key 时:放入 `pkg/constants/`,并补中文注释与 Key 生成函数。 - 写新 API 时:在 `internal/routes/*.go` 用 `Register()` + `RouteSpec` 注册,并同步更新 `cmd/api/docs.go` 与 `cmd/gendocs/main.go` 的文档 Handler 装配。 - 运行规范检查时:优先使用 `scripts/check-*.sh` 与 `make docs`;不要把 `README.md` 中的测试/覆盖率描述当成当前执行标准。 --- *Convention analysis: 2026-03-27*