Python Flask如何规避Azure网关230秒超时适配长耗时工作负载
解决方案
方案1:流式响应保持TCP连接活跃(无需修改客户端逻辑,最适配需求)
你提到的Azure 230秒超时仅在TCP连接无任何数据传输时触发,我们可以通过Flask的流式响应接口,在长任务运行过程中定期发送心跳数据,避免连接进入空闲状态,直接规避超时限制。
修改后的代码示例如下:
from flask import Flask, Response import time import threading app = Flask(__name__) # 临时存储长任务执行结果,生产环境可替换为Redis等共享存储 task_result = {} def run_long_task(task_id): # 执行你的计算密集型长任务 task_result[task_id] = super_long_process_function() @app.route('/data') def data(): # 生成唯一任务ID,生产环境建议使用uuid task_id = str(time.time()) # 启动后台线程运行长任务 task_thread = threading.Thread(target=run_long_task, args=(task_id,)) task_thread.daemon = True task_thread.start() def generate_stream(): # 每隔30秒发送一次心跳,远小于230秒的超时阈值 while task_id not in task_result: # 发送空格作为心跳内容,不会干扰最终结果解析 yield ' ' time.sleep(30) # 任务执行完成,返回最终结果并清理缓存 final_res = task_result.pop(task_id) yield final_res # 返回流式响应,关闭自动内容长度计算,允许分片传输 return Response(generate_stream(), content_type='text/plain')
注意事项:
- 如果返回内容为JSON格式,可以把心跳内容替换为JSON注释符
//,客户端解析最终结果时把前置的空格/注释过滤即可,也可以约定固定前缀的心跳格式,客户端自动过滤。 - Azure Web App的Python默认运行环境支持流式响应,无需额外修改服务端配置;本地测试如果发现心跳没有实时发送,检查本地WSGI服务器是否开启了输出缓冲,比如gunicorn需要添加
--no-sendfile参数关闭缓冲。
方案2:异步任务+客户端轮询(适合可修改客户端逻辑的场景)
如果允许调整客户端交互逻辑,可以采用稳定性更高的异步任务架构:
- 接口收到请求后立刻返回202状态码和唯一任务ID,将长任务提交到后台执行(高并发场景推荐用Celery等专业任务队列,低并发场景也可以用上述线程方案)
- 客户端拿到任务ID后,每隔几秒调用查询接口轮询任务状态,任务完成后查询接口返回最终结果
该方案完全规避了长连接的超时问题,适合生产环境大规模使用。
内容的提问来源于stack exchange,提问作者Neil
相关产品推荐
相关产品推荐

