7API Design Patterns

可靠性

API可靠性

幂等性重试超时错误处理

🎯 AI 时代的学习建议:不要只读理论。理解这一章的设计动机(为什么需要这个概念?)和边界条件(什么情况下会失效?)。当 AI 生成的代码涉及这些概念时,你能判断它是否用对了场景。AI 能帮你总结内容,但无法替代你亲手阅读、思考、建立直觉的过程。

第7章:可靠性(API Reliability)

一、导读

1.1 本章学习目标

第7章讲解 API 的可靠性设计——幂等性、重试、超时、错误处理。

本章的核心学习目标包括:

  • 理解幂等性的重要性
  • 掌握重试策略的设计
  • 学会设计超时和错误处理

1.2 为什么本章如此重要

网络不可靠——请求可能超时、重复、丢失。API 必须能处理这些情况,保证数据一致性和用户体验。

1.3 核心问题引导

什么是幂等性?为什么它很重要?

重试策略应该如何设计?

超时时间如何确定?

错误响应应该包含什么信息?


二、核心概念详解

2.1 幂等性

幂等性:多次执行与一次执行效果相同

HTTP 方法的幂等性:
- GET:幂等(读取不改变状态)
- PUT:幂等(替换为相同状态)
- DELETE:幂等(删除已删除的资源无影响)
- POST:非幂等(每次创建新资源)
- PATCH:通常幂等

实现幂等性:
POST /api/v1/payments
Idempotency-Key: req_abc123    // 客户端提供的幂等键

// 服务器用幂等键去重
// 相同幂等键的请求返回相同结果

2.2 重试策略

客户端重试策略:

1. 可重试的错误:
   - 5xx 服务器错误
   - 网络超时
   - 429 限流

2. 不可重试的错误:
   - 4xx 客户端错误(除了 429)
   - 非幂等操作的请求已发送

3. 退避策略:
   - 指数退避:1s, 2s, 4s, 8s...
   - 加随机抖动:避免雷群效应
   - 最大重试次数:3-5 次

4. 幂等键:
   - 非幂等操作必须使用幂等键
   - 确保重试安全

2.3 超时设计

超时层次:

1. 连接超时:建立连接的时间(5-10s)
2. 读取超时:等待响应的时间(根据操作类型)
   - 简单查询:5-10s
   - 列表操作:15-30s
   - 长运行操作:使用异步模式

3. 服务端超时:
   - 设置请求处理的最大时间
   - 超时返回 503 或 504

// 客户端配置
HttpClient client = HttpClient.builder()
    .connectTimeout(Duration.ofSeconds(5))
    .readTimeout(Duration.ofSeconds(30))
    .build();

2.4 错误处理

错误响应设计:

{
  "error": {
    "code": "RATE_LIMIT_EXCEEDED",
    "message": "Too many requests",
    "details": [
      {
        "type": "quota",
        "limit": 100,
        "remaining": 0,
        "resetAt": "2024-01-01T01:00:00Z"
      }
    ],
    "requestId": "req_abc123",
    "documentationUrl": "https://docs.example.com/errors/rate-limit"
  }
}

// 标准错误码
RATE_LIMIT_EXCEEDED    // 429
INVALID_ARGUMENT       // 400
NOT_FOUND             // 404
ALREADY_EXISTS        // 409
PERMISSION_DENIED     // 403
UNAUTHENTICATED       // 401
INTERNAL              // 500
UNAVAILABLE           // 503
DEADLINE_EXCEEDED     // 504

三、实战案例

3.1 案例一:幂等支付 API

POST /api/v1/payments
Idempotency-Key: pay_20240101_001
Content-Type: application/json
{
  "amount": 99.99,
  "currency": "USD",
  "customerId": "cust_123"
}

// 第一次请求
→ 201 Created
{
  "id": "pay_456",
  "status": "COMPLETED",
  "amount": 99.99
}

// 重试(相同幂等键)
POST /api/v1/payments
Idempotency-Key: pay_20240101_001
→ 201 Created(返回相同结果)
{
  "id": "pay_456",
  "status": "COMPLETED",
  "amount": 99.99
}

四、本章小结

幂等性:多次执行与一次执行效果相同。

重试策略:指数退避 + 随机抖动 + 幂等键。

超时设计:连接超时、读取超时、服务端超时。

错误处理:标准错误码、详细信息、文档链接。


五、思考与练习

如何为非幂等的 POST 操作实现幂等性?

设计一个完整的重试策略。

如何确定 API 的超时时间?


7/7可靠性
0%