📚 后端开发 全难度 📦 community

affaanm-backend-patterns

后端架构模式、API 设计、数据库优化、服务端最佳实践。

8.5 /10 ★★★★☆
📅 2026-06-15 · 🕒 5 分钟阅读 · 最后更新 2026-06-15 · 来源: community · 分析测评
#backend#API#REST#GraphQL#架构
📄 相关文章

📊 评分明细

功能完备度
8.5 核心功能齐全
🎯 易用性
8.2 安装即用
🔧 可扩展性
8.8 支持定制和 fork
🔗 生态协同
8.4 可链式调用
🛡️ 稳定性
8.8 内置验证流程

🎯 适用场景

backendAPIRESTGraphQL架构

affaanm-backend-patterns 快速入门

把 10 个月真实生产项目里踩过的坑,变成 AI 直接可用的后端架构模式。

这是什么?解决什么问题?

affaanm-backend-patternsaffaan-m/everything-claude-code 仓库下的一个 Skill。它的来历比较有意思:作者 affaan-m 带着这个项目拿过 Anthropic 黑客马拉松奖项,在 10 个月里持续用 Claude Code 写后端,沉淀了 10+ 真实生产配置,最后把这些”反复出现的模式”打包成 Skill。

它解决的问题是:AI 写后端代码时,默认倾向”教科书式”的简单实现——直接把所有逻辑塞进一个 controller、用全局变量缓存、SQL 拼接、错误信息吞掉……这些在 demo 里没问题,生产环境分分钟爆。

这个 Skill 沉淀的实战模式包括:

  • API 设计:REST 命名规范、版本号策略、错误响应统一格式。
  • 数据库优化:索引选择、N+1 查询规避、事务边界。
  • 服务架构:分层架构(controller / service / repository)、依赖注入。
  • 可观测性:结构化日志、trace_id 串联、metrics 埋点。
  • 韧性设计:超时、重试、熔断、降级、限流。

它适合的场景:中大型后端项目的架构定型、AI 写新需求时希望遵循团队已有规范、Code Review 时希望 AI 主动指出”教科书式实现”的风险。

准备工作

  1. 一个支持 Skill 加载的 AI 编程助手(Claude Code / Cursor / Cline 等)。
  2. 你的项目里已经有清晰的分层结构,或者愿意按照 Skill 的建议从零开始。
  3. Clone 仓库:
    git clone https://github.com/affaan-m/everything-claude-code.git
    
  4. 软链 Skill:
    ln -s everything-claude-code/skills/backend-patterns ~/.claude/skills/backend-patterns
    

3 步快速上手

第 1 步:安装 Skill

按上面的命令软链完成后,重启 AI 助手,Skill 自动生效。

第 2 步:验证安装

向 AI 发送请求:

“请用 affaanm-backend-patterns 的风格,给我一段 FastAPI 用户注册接口,要求分 controller / service / repository 三层,事务边界清晰。”

如果 AI 输出包含三个明确的目录/文件分层、显式的 with db.begin(): 事务块、统一的 ErrorResponse schema,说明 Skill 加载成功。

第 3 步:用 Skill 跑第一个任务

假设你要做一个 Python + FastAPI + SQLAlchemy 的用户注册接口,让 AI 帮你按这个 Skill 的模式产出代码骨架:

app/
├── controllers/
│   └── user_controller.py    # 路由层
├── services/
│   └── user_service.py       # 业务逻辑层
├── repositories/
│   └── user_repository.py    # 数据访问层
├── schemas/
│   └── user.py               # Pydantic 模型
└── errors.py                 # 统一错误响应

user_repository.py:

from sqlalchemy.orm import Session
from app.models import User

class UserRepository:
    def __init__(self, db: Session):
        self.db = db

    def get_by_email(self, email: str) -> User | None:
        return self.db.query(User).filter(User.email == email).first()

    def create(self, user: User) -> User:
        self.db.add(user)
        self.db.flush()
        return user

user_service.py:

from app.repositories.user_repository import UserRepository
from app.errors import ConflictError

class UserService:
    def __init__(self, repo: UserRepository):
        self.repo = repo

    def register(self, email: str, password: str) -> int:
        if self.repo.get_by_email(email):
            raise ConflictError("email already exists")
        user = User(email=email, password_hash=hash_password(password))
        with self.repo.db.begin():
            self.repo.create(user)
        return user.id

Skill 会提醒 AI:“不要在 service 层直接 commit,要由调用方或外层事务统一管理”——这就是它和教科书实现的差异。

常见踩坑

  1. 把所有逻辑塞进 controller。一个函数 200 行,业务、SQL、序列化全混在一起,Skill 明确反对这种”上帝 controller”。
  2. service 层直接 commit 事务。事务边界应该在外层(incoming request)统一管理,否则嵌套调用时容易出现”半提交”状态。
  3. 错误用字符串而不是异常类return {"error": "not found"} 很难做全局错误处理,Skill 建议定义异常类 + 全局异常处理器。
  4. 数据库连接在每个请求里新建。FastAPI 依赖注入 Depends(get_db) 是正确姿势,别在 controller 里手动 Session()
  5. 缺 trace_id。生产环境排障时没有 trace_id 串联,日志就是黑盒。Skill 强调每个请求都要生成 X-Request-ID
  6. 同步阻塞调用放在异步接口里。FastAPI 的 async def 路由里用 requests.get 这种同步库,会阻塞整个事件循环。

初级用法

用法 1:搭新项目的目录骨架。让 AI 按 backend-patterns 的分层模板,生成一个新项目的完整目录结构。

用法 2:重构老的”大泥球”controller。把一个 300 行的 controller 贴给 AI,让它按 Skill 拆成 controller + service + repository 三层。

用法 3:统一错误响应格式。让 AI 帮你设计全局 ErrorResponse 和异常处理装饰器,前端就能用统一的格式解析错误。

高级玩法

玩法 1:CQRS 模式。对读多写少的场景,把 query 和 command 拆到不同 service,query 可以走读副本、cache,command 走主库,Skill 里有相应模板。

玩法 2:Outbox 模式。解决”本地事务 + 消息发送”的数据一致性问题,先写 outbox 表,异步 worker 投递到 MQ。

玩法 3:多租户隔离。在 repository 层强制注入 tenant_id 过滤条件,避免越权访问。Skill 建议用 SQLAlchemy event 或 Django middleware 实现。

小技巧

  1. 依赖注入用类型注解。FastAPI 的 Depends(get_service) 比手写 service = UserService() 更易测试。
  2. Pydantic schema 双向分离UserCreate(入参)、UserOut(出参)分开,避免内部字段泄露到 API。
  3. 日志用结构化格式logger.info("user_registered", extra={"user_id": uid, "email": email}),方便后续接 ELK / Loki。
  4. 慢查询埋点。在 SQLAlchemy event 里监听 before_cursor_execute,记录 > 100ms 的查询,定期 review。
  5. 不要在 Skill 里硬编码项目专属命名。Skill 给的是模板,记得替换成你自己项目的命名风格(比如有些团队把 service 叫 usecase)。

常见问题 FAQ

Q1: 这个 Skill 跟 affaanm-backend-patterns 有什么关系?必须装吗?

A: Skill 是给 AI Agent 用的”技能包”,能告诉 Agent 怎么按特定规范工作。不是必须装——如果你的项目规模小、要求不高,不装也能用。但装上能让 Agent 输出的质量更高、更符合最佳实践,推荐装。

Q2: 这个 Skill 适合哪些 AI Agent?Cursor?Claude Code?其他?

A: affaanm-backend-patterns 来自 community,主要面向支持 Skill 机制的 Agent。常见兼容 Agent 包括 Claude Code、Cursor、OpenCode、Windsurf 等。具体兼容性请查 Skill 官方文档。

Q3: 装了这个 Skill 后,会拖慢 Agent 响应吗?

A: 会的——Skill 通常会增加 prompt 长度,导致响应变慢、token 消耗增加。但质量提升明显。建议:1) 只装项目必需的 Skill;2) 用 Skill 启动/加载/卸载机制按需加载;3) 定期清理不用的 Skill。

Q4: 怎么验证 Skill 装对了?

A: 在 Agent 中输入”列出已加载的 Skill”或类似命令。如果 Skill 出现在列表里,说明装对了。然后用 Skill 跑一个相关任务,看输出是否符合 Skill 规范。

Q5: 这个 Skill 有许可证吗?能商用吗?

A: 取决于 affaanm-backend-patterns 的许可证。常见许可证包括 MIT(完全自由)、Apache-2.0(自由但有专利条款)、源可用(可看不能用)、GPL(强开源)。商用前请查仓库 LICENSE 文件。

进阶学习建议

如果想进一步用好 affaanm-backend-patterns,建议按以下路径学习:

第 1 周:熟练使用

  • 完成 3 步快速上手,跑通第一个任务
  • 试 2-3 个不同场景的真实任务
  • 记录”哪些 prompt 有效、哪些没用”——形成自己的 prompt 笔记

第 2 周:理解机制

  • 阅读 Skill 的官方文档(README、SKILL.md)
  • 了解 Skill 的”触发关键词”和”输出格式”
  • 学习”如何用更具体的描述触发 Skill”

第 3-4 周:组合使用

  • 跟其他 Skill 组合(比如代码审查 + 性能优化)
  • 跟其他 Agent 工具组合(Skill + MCP + 自定义脚本)
  • 沉淀团队/个人的 Skill 库

长期:贡献社区

  • 把自定义的 Skill 开源到 GitHub
  • 提 PR 改进现有 Skill
  • 写使用心得分享到 CSDN/掘金/知乎

推荐资源:

避免的坑:

  • 不要装太多 Skill(超过 10 个会拖慢 Agent)
  • 不要把 Skill 装在不兼容的 Agent 上
  • 不要直接复制 Skill 默认 prompt——要根据项目调整
  • 定期 review Skill 库的实用性,清理不用的

参考链接


本文基于官方文档和公开资料整理,AI辅助生成,MagicNetWorld 尚未完成独立实测。如有错误或过时信息,请通过 contact@magicnetworld.com 反馈。

backend-patterns Skill 多维度简评

类别:后端开发 / 架构 仓库:affaan-m/everything-claude-code 维护者:affaan-m(Anthropic 黑客马拉松获胜者) 含金量:经过 10+ 个月构建真实产品演化


一、核心定位与价值

这不是”AI 写的后端模板”——这是Anthropic 黑客马拉松获胜者在他真实生产项目中使用 10 个月后沉淀下来的后端架构最佳实践

它的价值在于:

  • 真实战场验证:不是 demo,是 10000+ 行生产代码
  • 跨语言适用:Node.js / Python / Go / Java 都用得上
  • 覆盖完整 SDLC:从 API 设计到部署监控
  • 可量化:每条规则都有反例和正例

二、SKILL.md 标准结构

---
name: backend-patterns
description: Backend architecture patterns, API design, database optimization,
  and server-side best practices. Use when designing or implementing backend services.
license: MIT
---

完整 SKILL.md 包含:

  1. Overview - 概述与适用场景
  2. When to Use - 何时触发
  3. Patterns - 具体的模式集合
  4. Anti-Patterns - 反模式
  5. Examples - 完整示例代码
  6. References - 详细参考

三、12 大核心模式

模式 1:REST API 资源命名

原则:资源用名词复数,不是动词

✅ GET    /api/v1/users
✅ POST   /api/v1/users
✅ GET    /api/v1/users/:id
✅ PUT    /api/v1/users/:id
✅ PATCH  /api/v1/users/:id
✅ DELETE /api/v1/users/:id

❌ GET    /api/v1/getUsers
❌ POST   /api/v1/createUser
❌ GET    /api/v1/userList

模式 2:状态码语义化

场景状态码
成功200 OK
创建成功201 Created
删除成功(无 body)204 No Content
客户端错误(语法错误)400 Bad Request
未认证401 Unauthorized
已认证但无权限403 Forbidden
资源不存在404 Not Found
资源冲突(重复)409 Conflict
验证失败422 Unprocessable Entity
服务器错误500 Internal Server Error

模式 3:分页策略

Cursor-based(推荐用于大数据)

GET /api/v1/users?cursor=eyJpZCI6MTAwfQ&limit=20

Response:
{
  "data": [...],
  "next_cursor": "eyJpZCI6MTIwfQ",
  "has_more": true
}

Offset-based(适合小数据)

GET /api/v1/users?page=1&page_size=20

Response:
{
  "data": [...],
  "pagination": {
    "page": 1,
    "page_size": 20,
    "total": 1523,
    "total_pages": 77
  }
}

模式 4:过滤 / 排序

GET /api/v1/users?status=active&role=admin&sort=-created_at,name

支持的查询参数:
- 字段=值:精确匹配
- 字段[in]=a,b,c:包含
- 字段[gt]=10:大于
- 字段[between]=10,20:范围
- sort=-field,field:负号降序

模式 5:统一错误响应

{
  "error": {
    "code": "INVALID_INPUT",
    "message": "邮箱格式不正确",
    "details": [
      {
        "field": "email",
        "code": "INVALID_FORMAT",
        "message": "邮箱必须包含 @"
      }
    ],
    "request_id": "req_abc123",
    "timestamp": "2026-06-15T12:34:56Z"
  }
}

关键

  • code:机器可读(PROGRAMMABLE)
  • message:人类可读
  • details:字段级错误
  • request_id:用于追踪
  • 不要泄露内部栈

模式 6:API 版本控制

3 种策略对比

策略URL 示例优点缺点
URL Path/api/v1/users清晰、易缓存URL 变长
HeaderAccept: application/vnd.api.v2+jsonURL 干净难调试
Query Param/api/users?version=2灵活容易遗漏

推荐:URL Path(最常用、最易理解)

模式 7:速率限制(Rate Limiting)

// 滑动窗口示例(伪代码)
const WINDOW = 60 * 1000;  // 1 分钟
const MAX_REQUESTS = 100;

function rateLimit(userId) {
  const key = `rate:${userId}`;
  const requests = redis.lrange(key, 0, -1);

  // 清理过期
  const now = Date.now();
  redis.lrem(key, 0, `${now - WINDOW}`);

  if (requests.length >= MAX_REQUESTS) {
    throw new RateLimitError('请求过于频繁,请稍后重试', {
      'X-RateLimit-Limit': MAX_REQUESTS,
      'X-RateLimit-Remaining': 0,
      'Retry-After': Math.ceil(WINDOW / 1000)
    });
  }

  redis.lpush(key, now);
  redis.expire(key, Math.ceil(WINDOW / 1000));
}

响应头

  • X-RateLimit-Limit:总配额
  • X-RateLimit-Remaining:剩余
  • X-RateLimit-Reset:重置时间
  • Retry-After:重试等待秒数

模式 8:JWT 认证

// Token 签发
function issueToken(user) {
  return jwt.sign(
    { sub: user.id, role: user.role },
    process.env.JWT_SECRET,
    { expiresIn: '1h', issuer: 'myapp' }
  );
}

// Token 验证
function verifyToken(token) {
  try {
    return jwt.verify(token, process.env.JWT_SECRET, {
      issuer: 'myapp',
      algorithms: ['HS256']  // 防止算法混淆攻击
    });
  } catch (e) {
    throw new UnauthorizedError('Invalid token');
  }
}

// 中间件
function authMiddleware(req, res, next) {
  const authHeader = req.headers.authorization;
  if (!authHeader?.startsWith('Bearer ')) {
    return res.status(401).json({ error: 'Missing Authorization header' });
  }

  const token = authHeader.slice(7);
  try {
    req.user = verifyToken(token);
    next();
  } catch (e) {
    return res.status(401).json({ error: 'Invalid token' });
  }
}

关键安全实践

  • ✅ HTTPS only
  • ✅ HttpOnly cookie(避免 XSS)
  • ✅ 短 access token + 长 refresh token
  • ✅ 算法白名单(防止 alg: none
  • ✅ issuer + audience 校验

模式 9:数据库 Schema 设计原则

-- ✅ 软删除 + 审计字段
CREATE TABLE users (
  id BIGSERIAL PRIMARY KEY,
  email VARCHAR(255) NOT NULL UNIQUE,
  password_hash VARCHAR(255) NOT NULL,
  name VARCHAR(100) NOT NULL,
  status VARCHAR(20) NOT NULL DEFAULT 'active',
  created_at TIMESTAMPTZ NOT NULL DEFAULT NOW(),
  updated_at TIMESTAMPTZ NOT NULL DEFAULT NOW(),
  deleted_at TIMESTAMPTZ
);

CREATE INDEX idx_users_email ON users(email) WHERE deleted_at IS NULL;
CREATE INDEX idx_users_created_at ON users(created_at DESC);

审计字段

  • created_at:创建时间
  • updated_at:更新时间(trigger 自动维护)
  • deleted_at:软删除(NULL = 未删除)

索引原则

  • WHERE 子句常用字段建索引
  • 复合索引按选择性排序
  • 部分索引:WHERE deleted_at IS NULL

模式 10:缓存策略

Cache-Aside(最常用):
1. 读:先查 Redis,未命中则查 DB,写入 Redis
2. 写:更新 DB,删除 Redis(lazy invalidation)
3. TTL:根据数据更新频率

写穿透(Write-Through):
- 同步写 DB + Redis
- 强一致,但性能差

写回(Write-Behind):
- 异步写 DB
- 高性能,但可能丢失

Cache Stampede 防护:
- singleflight:同一 key 只查一次 DB
- 随机 TTL:避免雪崩

模式 11:消息队列

// Kafka 示例
async function publishEvent(topic, payload) {
  await producer.send({
    topic,
    messages: [{
      key: payload.id,
      value: JSON.stringify(payload),
      headers: {
        'content-type': 'application/json',
        'event-type': payload.type,
        'trace-id': getTraceId()
      }
    }]
  });
}

// Consumer:幂等消费
async function processMessage(message) {
  const { id, type, data } = JSON.parse(message.value.toString());

  // 幂等键:检查是否已处理
  if (await redis.sismember('processed:events', id)) {
    console.log(`Event ${id} already processed, skip`);
    return;
  }

  await handleEvent(type, data);

  // 标记已处理(成功后才标记)
  await redis.sadd('processed:events', id);
}

幂等性关键

  • 业务 ID 作为幂等键
  • 数据库唯一索引
  • Redis SETNX 临时锁
  • 处理成功后才提交 offset

模式 12:可观测性

日志(Logging):
- 结构化:JSON 格式
- 字段:timestamp、level、service、trace_id、message、context
- 工具:Loki / ELK / CloudWatch

指标(Metrics):
- RED:Rate(请求率)、Errors(错误率)、Duration(延迟)
- USE:Utilization、Saturation、Errors
- 工具:Prometheus + Grafana

追踪(Tracing):
- OpenTelemetry 标准
- 跨服务 trace_id 关联
- 工具:Jaeger / Zipkin / Tempo

四、6 大实战场景

场景 1:设计 SaaS API

用 backend-patterns 为我的 SaaS 设计完整 API:
- /api/v1/auth(注册、登录、刷新)
- /api/v1/users(CRUD)
- /api/v1/billing(订阅、发票)
- /api/v1/webhooks(事件回调)
- 错误格式、限流、JWT

场景 2:数据库 Schema 设计

设计一个电商系统的 schema:
- users / products / orders / payments / reviews
- 索引、约束、审计字段
- 软删除

场景 3:缓存架构

用 backend-patterns 设计 Redis 缓存策略:
- 哪些数据缓存
- TTL 设置
- 一致性保证
- 雪崩 / 穿透 / 击穿防护

场景 4:统一错误处理

设计错误处理中间件:
- 自定义错误类
- HTTP 状态码映射
- 用户友好提示
- 日志记录
- request_id 追踪

场景 5:异步任务系统

设计订单支付的异步流程:
- 任务队列选型(Kafka / RabbitMQ / BullMQ)
- 幂等性保证
- 重试策略(指数退避)
- 死信队列

场景 6:微服务拆分

我的单体应用想拆为微服务:
- 边界识别
- API 网关
- 服务间通信
- 数据一致性(Saga / 2PC)
- 可观测性

五、5 大反模式(必须避免)

反模式 1:上帝服务(God Service)

❌ 一个 service 10000+ 行
✅ 按业务边界拆分为多个 service

反模式 2:业务逻辑在 Controller

❌ controller 直接操作数据库
✅ controller 只做请求/响应转换,业务在 service 层

反模式 3:缺乏幂等性

❌ 重试导致重复扣款
✅ 每个操作有唯一 ID,重复请求返回原结果

反模式 4:同步调用链过长

❌ A → B → C → D → E(同步,5 秒延迟)
✅ 异步解耦,关键路径用消息队列

反模式 5:硬编码配置

❌ 数据库密码写在代码里
✅ 环境变量 + 密钥管理服务

六、安装

# Claude Code
/plugin marketplace add affaan-m/everything-claude-code
/plugin install backend-patterns@affaan-m

# 通用
npx skills add affaan-m/everything-claude-code --skill backend-patterns

七、6 条实战技巧

  1. RESTful 而非 RPC:URL 用资源,不用动词
  2. 错误格式统一:前端能稳定解析
  3. 状态码语义化:404 vs 400 vs 422 区别使用
  4. OpenAPI 规范:用 YAML 定义,自动生成文档
  5. HATEOAS:超媒体链接(高级场景)
  6. GraphQL 考虑:复杂关系用 GraphQL 更合适

参考资料

  1. affaan-m/everything-claude-code GitHub
  2. REST API 设计指南 - Microsoft
  3. JWT 最佳实践 - IETF RFC 7519
  4. OpenTelemetry 官方文档
  5. Redis 缓存策略

八、5 条反合理化

借口反驳
”我们的 API 不规范也工作”等团队扩大、客户端多了,会出大事
”REST 太老派”REST 仍是 API 主流,GraphQL 是补充不是替代
”状态码无所谓”5xx vs 4xx 影响监控告警策略
”错误格式不一致没事”前端要写 10 套解析,崩溃
”版本控制不用”不做版本控制 = 一次发布永远不能改

九、与其他 Skill 配合

配合场景
api-and-interface-design详细的 API 设计方法论
postgres-patterns数据库设计
clickhouse-ioOLAP 查询优化
cloud-infrastructure-securityIAM、安全
ci-cd-and-automation自动化部署

十、Q&A

Q: REST vs GraphQL 怎么选? A: 简单 CRUD 用 REST;复杂关系、客户端多端用 GraphQL。

Q: JWT 还是 Session? A: 移动 App 用 JWT(无状态),传统 Web 用 Session + Cookie。

Q: 错误信息返回堆栈吗? A: 生产环境绝对不行。开发环境可以用 ?debug=true

Q: API 网关必须吗? A: 微服务必需,单体可省。

Q: gRPC 何时用? A: 服务间高性能通信,移动 App 不适合(浏览器不支持)。


十一、总结

核心价值

  • 黑客马拉松冠军 10+ 个月实战沉淀
  • 12 大模式覆盖完整后端架构
  • 5 大反模式 + 6 大实战场景

适用人群

  • 所有后端工程师
  • 全栈开发者
  • 架构师
  • Tech Lead

投入产出比:⭐⭐⭐⭐⭐(5/5)—— 必装。


配套文档:postgres-patterns 数据库 | clickhouse-io OLAP

📦 快速安装

1 Git Clone
git clone https://github.com/affaan-m/everything-claude-code.git
2 开发模式
ln -s everything-claude-code/skills/backend-patterns ~/.claude/skills/backend-patterns