http通过StreamingHttpResponse完成连续的数据传输长链接方式


Posted in Python onFebruary 12, 2022

http通过StreamingHttpResponse完成连续的数据传输长链接

问题

http服务之间传递结果流

一个由flask封装起来的算法,一个由django封装的后台,我希望在django里通过requests调用flask的算法接口,flask可以分析一帧返回一帧结果,追求分析结果的实时返回,而不是完全分析完再完整返回结果

为了能完整返回结果,暂时想到的模式有以下三种:

  • 一问一答:等待完整的分析结果,然后返回,最不济就用这种
  • 我要你给(长链接):flask返回一个generator,django取next就得到下一个的结果
  • 你有你给(理想,长链接):建立长链接,flask每分析出一帧结果,就返回

一次结果,直到分析结束,关闭连接

看到flask中有个flask_socketio建立socket连接,还没有实验

暂时用StreamingHttpResponse,generater能实现实时分析的感觉,属于第三种模式(你有你给)

django的StreamingHttpResponse可以返回generater,request调用返回generate的接口的时候,通过contextlib 的closing对流进行处理:

输出

#django 算法端,输出流
from django.http import StreamingHttpResponse
def stream_response(request):                  
    def generate():                            
        for i in range(10):                    
            print(i)                           
            yield 'hi ' + str(i)               
            print('sleep 3')                   
            time.sleep(1)                      
    return StreamingHttpResponse(generate(), ) 
#flask 算法端,输出流
@app.route('/re', methods=('POST', ))
def re():
    @flask.stream_with_context
    def generate():
        for i in range(10):                    
            print(i)                           
            yield 'hi ' + str(i)
            print('sleep 3')                   
            time.sleep(1)
    return flask.Response(generate())

输入

不区分flask,django,都可以通过request,contextlib 实现

#flask 算法端
@app.route('/test', methods=['POST', 'GET'])
def test():
    url = 'http://172.16.68.151:8000/test2'
    from contextlib import closing
    with closing(requests.get(url, stream=True)) as r1:
        for i in r1.iter_content():
            print(i)

StreamingHttpResponse和HttpResponse

在修改以前的文件下载功能时,发现一个文件有5G,用HttpResponse实现时,服务器返回502错误,查看nginx log时,发现nginx log记录的是: upstream prematurely closed connection while reading response header from upstream。应该是nginx服务器从上游获取数据时超时了。

查了很多办法,修改了nginx的配置,但是仍然超时。

绝望之下,查了一下Django的文档,发现了StreamingHttpResponse,试了一下效率提高了很多。

后来仔细查了一下发现HttpResponse在使用文件迭代器时:

HttpResponse will consume the iterator immediately, store its content as a string, and discard it.

HttpResponse会直接使用迭代器对象,将迭代器对象的内容存储城字符串,然后返回给客户端,同时释放内存。可以当文件变大看出这是一个非常耗费时间和内存的过程。

而StreamingHttpResponse是将文件内容进行流式传输,

StreamingHttpResponse在官方文档的解释是:

The StreamingHttpResponse class is used to stream a response from Django to the browser. You might want to do this if generating the response takes too long or uses too much memory.

这是一种非常省时省内存的方法。但是因为StreamingHttpResponse的文件传输过程持续在整个response的过程中,所以这有可能会降低服务器的性能。

参考文档

以上为个人经验,希望能给大家一个参考,也希望大家多多支持三水点靠木。

Python 相关文章推荐
在Python中使用HTMLParser解析HTML的教程
Apr 29 Python
python实现马耳可夫链算法实例分析
May 20 Python
Django 导出 Excel 代码的实例详解
Aug 11 Python
Python基于回溯法子集树模板实现8皇后问题
Sep 01 Python
python正则表达式爬取猫眼电影top100
Feb 24 Python
Python实现按中文排序的方法示例
Apr 25 Python
利用python库在局域网内传输文件的方法
Jun 04 Python
实例讲解python中的序列化知识点
Oct 08 Python
基于matplotlib中ion()和ioff()的使用详解
Jun 16 Python
详细分析Python collections工具库
Jul 16 Python
如何利用Python写个坦克大战
Nov 18 Python
python opencv实现直线检测并测出倾斜角度(附源码+注释)
Dec 31 Python
python中出现invalid syntax报错的几种原因分析
Feb 12 #Python
python ConfigParser库的使用及遇到的坑
Feb 12 #Python
Python制作春联的示例代码
Jan 22 #Python
Python制作表白爱心合集
基于Python实现一个春节倒计时脚本
Jan 22 #Python
详解Python如何批量采集京东商品数据流程
Jan 22 #Python
用Python实现屏幕截图详解
Jan 22 #Python
You might like
php中$_REQUEST、$_POST、$_GET的区别和联系小结
2011/11/23 PHP
php mssql扩展SQL查询中文字段名解决方法
2012/10/15 PHP
PHP+FastCGI+Nginx配置PHP运行环境
2014/08/07 PHP
php获取远程图片并下载保存到本地的方法分析
2016/10/08 PHP
php可变长参数处理函数详解
2017/02/22 PHP
php str_getcsv把字符串解析为数组的实现方法
2017/04/05 PHP
Laravel 实现密码重置功能
2018/02/23 PHP
Laravel利用gulp如何构建前端资源详解
2018/06/03 PHP
图片延迟加载的实现代码(模仿懒惰)
2013/03/29 Javascript
js验证输入是否为手机号码或电话号码示例
2013/12/30 Javascript
JS实现简单路由器功能的方法
2015/05/27 Javascript
创建基于Bootstrap的下拉菜单的DropDownList的JQuery插件
2016/06/02 Javascript
jQuery基于ID调用指定iframe页面内的方法
2016/07/06 Javascript
微信小程序 小程序制作及动画(animation样式)详解
2017/01/06 Javascript
如何使用Bootstrap创建表单
2017/03/29 Javascript
JS实现加载时锁定HTML页面元素的方法
2017/06/24 Javascript
让div运动起来 js实现缓动效果
2017/07/06 Javascript
jQuery中可见性过滤器简单用法示例
2018/03/31 jQuery
layer弹窗在键盘按回车将反复刷新的实现方法
2019/09/25 Javascript
JS script脚本中async和defer区别详解
2020/06/24 Javascript
javaScript实现一个队列的方法
2020/07/14 Javascript
[20:30]职业巡回赛回顾
2018/08/09 DOTA
Python中线程的MQ消息队列实现以及消息队列的优点解析
2016/06/29 Python
python中requests爬去网页内容出现乱码问题解决方法介绍
2017/10/25 Python
浅谈flask截获所有访问及before/after_request修饰器
2018/01/18 Python
Python面向对象class类属性及子类用法分析
2018/02/02 Python
python实现在一个画布上画多个子图
2020/01/19 Python
基于Python 的语音重采样函数解析
2020/07/06 Python
详解python实现可视化的MD5、sha256哈希加密小工具
2020/09/14 Python
CSS3教程(2):网页边框半径和网页圆角
2009/04/02 HTML / CSS
欧洲有机婴儿食品最大的市场:Organic Baby Food(供美国和加拿大)
2018/03/28 全球购物
介绍一下Mysql的存储引擎
2015/02/12 面试题
计算机专业毕业生自荐信范文
2014/03/06 职场文书
党建工作目标管理责任书
2015/01/29 职场文书
用Python提取PDF表格的方法
2021/04/11 Python
python plt.plot bar 如何设置绘图尺寸大小
2021/06/01 Python