我的AWS Lambda函数耗尽了何种资源导致无法扩展?
Lambda多线程读取DynamoDB无法扩展的资源瓶颈分析
问题背景
以下是一个使用多线程从AWS DynamoDB读取10000个约40KB小对象的AWS Lambda函数:
import boto3 import threading import math import json class DynamoDB: def __init__(self, table_name): self.client = boto3.client('dynamodb', region_name="us-east-1") self.table_name = table_name # 批量读取 def read(self, keys): batch_keys = { self.table_name: {'Keys': [{'content_id': {'S': id}} for id in keys]}} return self.client.batch_get_item(RequestItems=batch_keys) dynamodb = DynamoDB("mytable") def read_vectors(keys): batch_size = 100 n_batches = math.ceil(len(keys)/batch_size) for i in range(n_batches): my_keys = keys[i * batch_size : (i + 1) * batch_size] dynamodb.read(my_keys) def concurrent_reads(keys, n_threads): threads = [] keys_per_thread = math.ceil(len(keys)/n_threads) for i in range(n_threads): my_keys = keys[i * keys_per_thread : (i + 1) * keys_per_thread] thread = threading.Thread(target=read_vectors, args=(my_keys,)) thread.start() threads.append(thread) for thread in threads: thread.join() def lambda_handler(event, context): keys = [f"vectors/{content_id}" for content_id in range(10000)] concurrent_reads(keys, 5) # 5个线程 return { 'statusCode': 200, 'body': json.dumps('Hello from Lambda!') }
性能测试结果
线程数 耗时(秒) 1 10.5 2 7.1 3 5.5 4 5.2 5 5.4
已知条件
- 使用2048 MB和10240 MB内存时,性能表现相似
- 所有对象总大小为400 MB,Lambda与DynamoDB在同一区域运行
- 未耗尽网络带宽(10240 MB内存的Lambda理论带宽约25 GiB/s)
提问
我的Lambda函数耗尽了何种资源导致无法扩展?
核心瓶颈:DynamoDB的并发读取容量限制
1. 表级别的读容量(RCU)限流
DynamoDB的读能力由**读容量单位(RCU)**控制:
- 1个RCU对应每秒1次4KB的强一致性读,或2次最终一致性读
- 你的每个对象约40KB,因此读取1个对象需要10个RCU(40KB/4KB)
- 10000个对象的总RCU需求为100000,但默认预置表的RCU上限极低,即使是按需模式,突发容量也仅约3000 RCU(根据表规模)
当并发请求超过表的可用RCU时,DynamoDB会触发节流(Throttling),请求进入排队等待状态,此时新增Lambda线程不仅无法提升吞吐量,反而会因为重试等待增加额外开销,这就是线程数从4增加到5时耗时反而上升的原因。
2. batch_get_item API的请求速率限制
每个batch_get_item请求最多可读取100个项目或16MB数据(你的请求单批次4MB,未达大小限制),但DynamoDB对账户级别的batch_get_item请求速率有默认阈值。多线程并发发起大量批量请求时,会触发账户层面的限流,进一步限制性能提升。
验证方式
查看DynamoDB的CloudWatch指标ReadThrottleEvents,如果该指标数值大于0,即可确认存在节流现象。
优化建议
- 调整DynamoDB表的读容量:若使用预置模式,提高RCU值;若使用按需模式,可考虑短时间内提升容量或启用自动扩缩容
- 控制并发请求数:减少Lambda线程数,避免过度触发DynamoDB限流
- 使用DynamoDB Accelerator (DAX):通过缓存热点数据降低对DynamoDB后端的读取压力
- 优化读取模式:若业务允许,使用最终一致性读将RCU消耗减半
内容的提问来源于stack exchange,提问作者AlwaysLearning
相关产品推荐
相关产品推荐

