

# REL05-BP02 限制请求
<a name="rel_mitigate_interaction_failure_throttle_requests"></a>

限制请求，以防范因需求意外增加而导致的资源耗尽的情况。系统将处理未超过限制速率的请求，而超过所定义限制的请求将被拒绝，并返回一条消息，指出请求已受限制。

 **期望的结果：** 使用请求限制可以缓解客户流量突增、泛洪攻击或重试风暴所造成的大量容量峰值情况，让工作负载能够继续正常处理支持的请求量。 

 **常见反模式：** 
+  未实施 API 端点限制，或者未考虑预期容量即保留默认值。 
+  API 端点未经过负载测试，也未测试节流限制。 
+  限制请求速率而未考虑请求大小或复杂性。 
+  测试最大请求速率或最大请求大小，但未同时测试两者。 
+  资源预置的限制与测试中确定的限制不同。 
+  尚未为应用程序到应用程序的（A2A）API 使用者配置或考虑使用量计划。 
+  横向扩展的队列使用者没有配置最大并发设置。 
+  没有基于每个 IP 地址实施速率限制。 

 **建立此最佳实践的好处：** 在遇到意外的容量峰值时，设置了节流限制的工作负载能够正常运行，并成功处理已接受的请求负载。API 和队列上突然或持续出现的请求峰值会受到限制，不会耗尽请求处理资源。速率限制会限制单独的请求者，这样来自单个 IP 地址或 API 使用者的大量流量就不会耗尽资源，从而不会影响其他使用者。 

 **未建立这种最佳实践的情况下暴露的风险等级：** 高 

## 实施指导
<a name="implementation-guidance"></a>

 服务应设计为处理已知的请求容量；这种容量可以通过负载测试来确立。如果请求到达速率超过限制，则会发出相应的响应，表示请求已被限制。这让使用者可以处理错误并稍后重试。 

 当您的服务需要实施节流时，可以考虑实施令牌存储桶算法，每个令牌对应于一个请求。令牌按照每秒的限制速率重新填充，并按照每个请求一个令牌的模式异步清空。 

![描述令牌存储桶算法的图表。](http://docs.aws.amazon.com/zh_cn/wellarchitected/2023-04-10/framework/images/token-bucket-algorithm.png)


 

 [Amazon API Gateway](https://aws.amazon.com/api-gateway/) 根据账户和区域限制实施令牌存储桶算法，可通过使用量计划为每个客户端配置。此外，[Amazon Simple Queue Service（Amazon SQS）](https://aws.amazon.com/sqs/) 和 [Amazon Kinesis](https://aws.amazon.com/kinesis/) 可以缓冲请求以稳定请求速率，并在有足够的请求处理能力时实现更高的限制速率。最后，您可以通过 [AWS WAF](https://aws.amazon.com/waf/) 实施速率限制，以限制产生过高负载的特定 API 使用者。 

## 实施步骤
<a name="implementation-steps"></a>

 您可以为 API 配置具有节流限制的 API Gateway，并在超出限制时返回 `“429 请求过多”` 错误。您可以将 AWS WAF 与 AWS AppSync 和 API Gateway 端点结合使用，根据各个 IP 地址来启用速率限制。此外，如果您的系统能够接受异步处理，则可以将消息放入队列或流中，以加快对服务客户端的响应，这样您便可以突增到更高的限制速率。 

 使用异步处理，当您配置 Amazon SQS 作为 AWS Lambda 的事件源时，您可以 [配置最大并发度](https://docs.aws.amazon.com/lambda/latest/dg/with-sqs.html#events-sqs-max-concurrency) ，以避免高速率的事件消耗账户中可用的并发执行配额，因为您的工作负载或账户中的其他服务会需要这些配额。 

 虽然 API Gateway 提供了令牌存储桶的托管实施，但在无法使用 API Gateway 的情况下，您可以针对服务利用具体语言的令牌存储桶开源实施（参见“资源”中的相关示例）。 
+  了解和配置 [API Gateway 节流限制](https://docs.aws.amazon.com/apigateway/latest/developerguide/api-gateway-request-throttling.html) ：对于区域在账户级别，对于阶段在 API 级别，而对于使用量计划级别则为 API 密钥。 
+  应用 [AWS WAF 速率限制规则](https://aws.amazon.com/blogs/security/three-most-important-aws-waf-rate-based-rules/) 到 API Gateway 和 AWS AppSync 端点，以阻止泛洪攻击并屏蔽恶意 IP。对于 A2A 使用者，也可以在 AWS AppSync API 密钥上配置速率限制规则。 
+  对于 AWS AppSync API，请考虑您需要的节流控制是否超过了速率限制，如果超过，请在 AWS AppSync 端点前面配置 API Gateway。 
+  将 Amazon SQS 队列设置为 Lambda 队列使用者的触发器时，请将 [最大并发度](https://docs.aws.amazon.com/lambda/latest/dg/with-sqs.html#events-sqs-max-concurrency) 设置为一个值，使其处理量足以满足服务等级目标，同时使用量又不会超过并发度限制而影响其他 Lambda 函数。当您通过 Lambda 使用队列时，请考虑为相同账户和区域中的其他 Lambda 函数设置预留并发度。 
+  将 API Gateway 与 Amazon SQS 或 Kinesis 的原生服务集成结合使用，以缓冲请求。 
+  如果您无法使用 API Gateway，请查看具体语言的库，以便为工作负载实施令牌存储桶算法。查看示例部分，然后自行研究以查找合适的库。 
+  对您计划设置的限制或者您计划允许增加的限制进行测试，并记录测试后的限制值。 
+  不要将限制值提高到超出您在测试中确立的限制值。增加限制时，请先确认预置的资源是否已经等于或大于测试场景中预置的资源，然后再进行增加。 

## 资源
<a name="resources"></a>

 **相关最佳实践：** 
+  [REL04-BP03 持续工作](rel_prevent_interaction_failure_constant_work.md) 
+  [REL05-BP03 控制与限制重试调用](rel_mitigate_interaction_failure_limit_retries.md) 

 **相关文档：** 
+  [Amazon API Gateway：限制 API 请求以提高吞吐量](https://docs.aws.amazon.com/apigateway/latest/developerguide/api-gateway-request-throttling.html) 
+ [AWS WAF：基于速率的规则语句 ](https://docs.aws.amazon.com/waf/latest/developerguide/waf-rule-statement-type-rate-based.html)
+ [ 引入了使用 Amazon SQS 作为事件源时 AWS Lambda 的最大并发度 ](https://aws.amazon.com/blogs/compute/introducing-maximum-concurrency-of-aws-lambda-functions-when-using-amazon-sqs-as-an-event-source/)
+ [AWS Lambda：最大并发度 ](https://docs.aws.amazon.com/lambda/latest/dg/with-sqs.html#events-sqs-max-concurrency)

 **相关示例：** 
+ [ 三条最重要的基于 AWS WAF 速率的规则 ](https://aws.amazon.com/blogs/security/three-most-important-aws-waf-rate-based-rules/)
+ [ Java Bucket4j ](https://github.com/bucket4j/bucket4j)
+ [ Python token-bucket ](https://pypi.org/project/token-bucket/)
+ [ Node token-bucket ](https://www.npmjs.com/package/tokenbucket)
+ [ .NET 系统线程速率限制 ](https://www.nuget.org/packages/System.Threading.RateLimiting)

 **相关视频：** 
+ [ 使用 AWS AppSync 实施 GraphQL API 安全最佳实践 ](https://www.youtube.com/watch?v=1ASMLeJ_15U)

 **相关工具：** 
+ [ Amazon API Gateway ](https://aws.amazon.com/api-gateway/)
+ [AWS AppSync](https://aws.amazon.com/appsync/)
+ [ Amazon SQS ](https://aws.amazon.com/sqs/)
+ [ Amazon Kinesis ](https://aws.amazon.com/kinesis/)
+ [AWS WAF](https://aws.amazon.com/waf/)