# 最佳实践

## 配置管理

推荐：把监听地址、认证、超时、外部 adapter endpoint、采样率等放入配置结构，并使用环境变量覆盖敏感部署差异。

反例：在 handler 中硬编码 endpoint、token 或生产环境参数。

## 错误处理

推荐：在框架边界转换为统一错误和 `ApiResponse`，保留可诊断消息。

反例：在业务代码中 `unwrap()` 外部输入、数据库结果或网络调用。

## 超时、限流和熔断

推荐：外部调用必须配置 timeout；高并发入口使用 concurrency limit；不稳定依赖使用 circuit breaker；入口服务在压测后开启 adaptive shedding；需要跨实例配额时接入 Redis limiter，并明确 fail-open 或 fail-closed 策略。

反例：把所有失败都无限重试，或让请求等待外部依赖直到连接自然超时；把原始 URL、用户 ID 或错误消息作为韧性指标 label。

限流 key 推荐使用 route pattern、service、method、tenant tier 等低基数字段；不要使用 raw path、完整 Redis key、手机号、用户 ID 或请求参数。

## 认证与 public path

推荐：默认保护业务路由，只把 `/ready`、`/metrics` 等明确 endpoint 加入 public allowlist。

反例：开发时为了方便关闭认证后忘记恢复。

## Request ID

推荐：入口处生成或透传 request-id，并在 REST/RPC/log/trace 中持续传递。

反例：只在日志里打印随机 ID，但不通过响应头或 RPC metadata 透出。

## Observability

推荐：REST 服务暴露基础 metrics；跨服务调用启用 tracing；日志使用低基数 correlation 字段，subscriber 输出层脱敏；OTLP exporter 要配置 shutdown/flush。

反例：只在本地打印日志，生产环境没有请求维度指标；把 raw path、用户 ID、token、SQL 参数或 Redis key 写入日志关联字段。

## TraceContext

推荐：入口解析 `traceparent`，出站 RPC 使用 `trace_context_interceptor` 透传当前 trace context；没有活跃 OTLP context 时不要伪造 trace id。

反例：每个服务自己生成不兼容的 trace id，导致链路无法串联。

## Cache key

推荐：cache key 使用稳定 namespace 和索引列顺序，例如 `user:email:mobile:{}`。

反例：把业务对象 JSON 直接作为 key，或不同模块各自拼接不同格式。

## Cache-aside

推荐：读权威数据源前先走 cache-aside helper，让同 key 并发 miss 合并，并为 not found 结果设置短 TTL 负缓存。

反例：每个请求 miss 后都直接打到数据库，或把 Redis 写入错误静默吞掉。

## Cache delete retry

推荐：写后删缓存失败时开启有界 retry，并监控 retry dropped/failed 情况。

反例：无限后台重试，或在删除失败后假装写入链路完全成功。

## 代码生成

推荐：生成文件进入独立目录，默认不覆盖；需要覆盖时显式使用 `--force` 并先查看 diff。

反例：把生成命令直接指向手写业务目录并强制覆盖。

## 测试策略

推荐：默认 CI 只跑无外部依赖测试；外部服务测试使用 ignored 或 feature gate。

反例：默认测试依赖本机 Redis、etcd、Kubernetes 或 OTLP collector。

## 文档维护

推荐：新增能力时同步 README 导航、相关手册、教程和测试链接。

反例：只更新里程碑记录，不告诉新用户如何使用。
