Python websocket-client连接AWS DynamoDB Streams时自动断开问题咨询
问题解决方案
1. 为什么会出现“going away”断开?
AWS API Gateway WebSocket默认有闲置超时机制(默认30分钟,可配置最长2小时),当连接长时间无数据收发时,AWS会主动断开连接。同时websocket-client的run_forever默认无内置心跳,无法主动维持连接活性,闲置后就会触发断开。
2. 如何维持长连接?
(1)添加心跳机制
通过websocket-client的ping_interval和ping_timeout参数,定期发送Ping帧让AWS感知连接仍活跃:
ws.run_forever( ping_interval=300, # 每5分钟发送一次Ping ping_timeout=60 # 等待Pong响应的超时时间 )
这个设置会让客户端自动发送Ping,AWS收到后回复Pong,避免因闲置被断开。
(2)手动实现重连逻辑
即便加了心跳,网络波动或AWS端异常仍可能导致断开,因此必须配合自动重连逻辑。可以在on_close回调中触发重连,或用循环包裹连接逻辑:
import websocket import time def on_message(ws, message): print(f"收到更新: {message}") def on_error(ws, error): print(f"错误: {error}") def on_close(ws, close_status_code, close_msg): print(f"连接关闭,状态码: {close_status_code}, 消息: {close_msg}") # 等待5秒后尝试重连 time.sleep(5) start_websocket() def on_open(ws): print("连接成功") def start_websocket(): ws = websocket.WebSocketApp( "你的AWS WebSocket端点", on_open=on_open, on_message=on_message, on_error=on_error, on_close=on_close ) ws.run_forever(ping_interval=300, ping_timeout=60) if __name__ == "__main__": start_websocket()
这样断开后会自动重试连接,保障服务连续性。
(3)调整AWS端超时配置
登录AWS控制台,找到你的API Gateway WebSocket API,进入“设置”页面,将“闲置超时”调整到最大值(2小时),配合心跳机制可最大化连接时长。
3. AWS WebSocket长连接的成本对比
WebSocket比轮询划算得多:
- 轮询:若每秒发起一次请求,单个用户每天会产生86400次API调用,长期下来API调用成本极高。
- WebSocket:成本由两部分组成:
- 连接时长:每百万分钟约$0.6,单个连接每天1440分钟,100个用户每天仅约$0.086。
- 消息收发:每百万条消息约$0.1,仅在DynamoDB有更新时才会发消息,远少于轮询的请求量。
只要用户量不是极大,WebSocket的成本远低于轮询方案。
额外建议
- 不要依赖
run_forever默认行为,心跳+重连是WebSocket长连接的标准实践。 - 重连时可添加指数退避(如第一次等5秒,第二次10秒,第三次20秒),避免频繁重试给AWS造成压力。
- 测试时可故意断开网络,验证重连逻辑是否生效。
内容的提问来源于stack exchange,提问作者daoplays
相关产品推荐
相关产品推荐

