Django如何使用asyncio协程和ThreadPoolExecutor多线程


Posted in Python onOctober 12, 2020

Django视图函数执行,不在主线程中,直接loop = asyncio.new_event_loop()
# 不能loop = asyncio.get_event_loop() 会触发RuntimeError: There is no current event loop in thread

因为asyncio程序中的每个线程都有自己的事件循环,但它只会在主线程中为你自动创建一个事件循环。所以如果你asyncio.get_event_loop在主线程中调用一次,它将自动创建一个循环对象并将其设置为默认值,但是如果你在一个子线程中再次调用它,你会得到这个错误。相反,您需要在线程启动时显式创建/设置事件循环:

loop = asyncio.new_event_loop()
asyncio.set_event_loop(loop)

在Django单个视图中使用asyncio实例代码如下(有多个IO任务时)

from django.views import View
import asyncio
import time
from django.http import JsonResponse
 
 
class TestAsyncioView(View):
  def get(self, request, *args, **kwargs):
    """
    利用asyncio和async await关键字(python3.5之前使用yield)实现协程
    """
    self.id = 5
    start_time = time.time()
 
    '''
    # 同步执行
    # results = [self.io_task1(self.id),
    # self.io_task2(self.id),
    # self.io_task2(self.id)]
    '''
 
 
    loop = asyncio.new_event_loop() # 或 loop = asyncio.SelectorEventLoop()
    asyncio.set_event_loop(loop)
    self.loop = loop
 
    works = [
      asyncio.ensure_future(self.io_task3(5)),
      asyncio.ensure_future(self.io_task3(5)),
      asyncio.ensure_future(self.io_task3(5)),
      asyncio.ensure_future(self.io_task3(5)),
      asyncio.ensure_future(self.io_task3(5)),
 
    ]
 
    try:
 
      results = loop.run_until_complete(asyncio.gather(*works)) # 两种写法
      # results = loop.run_until_complete(self.gather_tasks())
    finally:
      loop.close()
    end_time = time.time()
    return JsonResponse({'results': results, 'cost_time': (end_time - start_time)})
 
  async def gather_tasks(self):
 
    tasks = (
      self.make_future(self.io_task1, self.id),
      self.make_future(self.io_task2, self.id),
      self.make_future(self.io_task2, self.id),
      self.make_future(self.io_task1, self.id),
      self.make_future(self.io_task2, self.id),
      self.make_future(self.io_task2, self.id),
    )
    results = await asyncio.gather(*tasks)
    return results
 
  async def make_future(self, func, *args):
    future = self.loop.run_in_executor(None, func, *args)
    response = await future
    return response
 
  def io_task1(self, sleep_time):
    time.sleep(sleep_time)
    return 66
 
  def io_task2(self, sleep_time):
    time.sleep(sleep_time)
    return 77
 
  async def io_task3(self, sleep_time):
    # await asyncio.sleep(sleep_time)
    s = await self.do(sleep_time)
    return s
 
  async def do(self, sleep_time):
    await asyncio.sleep(sleep_time)
    return 66

在Django单个视图中使用ThreadPoolExecutor实例代码如下(有多个IO任务时)

from django.views import View
import time
from concurrent.futures import ThreadPoolExecutor, as_completed
 
 
class TestThreadView(View):
  def get(self, request, *args, **kargs):
    start_time = time.time()
    future_set = set()
    tasks = (self.io_task1, self.io_task2, self.io_task2, self.io_task1, self.io_task2, self.io_task2)
    with ThreadPoolExecutor(len(tasks)) as executor:
      for task in tasks:
        future = executor.submit(task, 5)
        future_set.add(future)
    for future in as_completed(future_set):
      error = future.exception()
      if error is not None:
        raise error
    results = self.get_results(future_set)
    end_time = time.time()
    return JsonResponse({'results': results, 'cost_time': (end_time - start_time)})
 
  def get_results(self, future_set):
 
    results = []
    for future in future_set:
      results.append(future.result())
    return results
 
  def io_task1(self, sleep_time):
    time.sleep(sleep_time)
    return 66
 
  def io_task2(self, sleep_time):
    time.sleep(sleep_time)
    return 77

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Python 相关文章推荐
python发腾讯微博代码分享
Jan 10 Python
python日志记录模块实例及改进
Feb 12 Python
在Django中输出matplotlib生成的图片方法
May 24 Python
Python3使用turtle绘制超立方体图形示例
Jun 19 Python
django利用request id便于定位及给日志加上request_id
Aug 26 Python
解决python 未发现数据源名称并且未指定默认驱动程序的问题
Dec 07 Python
Python 简单计算要求形状面积的实例
Jan 18 Python
python字典和json.dumps()的遇到的坑分析
Mar 11 Python
Python+Kepler.gl实现时间轮播地图过程解析
Jul 20 Python
python装饰器实现对异常代码出现进行自动监控的实现方法
Sep 15 Python
使用python-cv2实现Harr+Adaboost人脸识别的示例
Oct 27 Python
Python Matplotlib库实现画局部图
Nov 17 Python
使用Python中tkinter库简单gui界面制作及打包成exe的操作方法(二)
Oct 12 #Python
使用Python将xmind脑图转成excel用例的实现代码(一)
Oct 12 #Python
使用python把xmind转换成excel测试用例的实现代码
Oct 12 #Python
Python Sqlalchemy如何实现select for update
Oct 12 #Python
浅析PyCharm 的初始设置(知道)
Oct 12 #Python
Pandas替换及部分替换(replace)实现流程详解
Oct 12 #Python
Django windows使用Apache实现部署流程解析
Oct 12 #Python
You might like
php中$_SERVER[PHP_SELF] 和 $_SERVER[SCRIPT_NAME]之间的区别
2009/09/05 PHP
ThinkPHP框架获取最后一次执行SQL语句及变量调试简单操作示例
2018/06/13 PHP
javascript 循环读取JSON数据的代码
2010/07/17 Javascript
JavaScript去掉空格的方法集合
2010/12/28 Javascript
js单独获取一个checkbox看其是否被选中
2014/09/22 Javascript
node.js中的events.emitter.listeners方法使用说明
2014/12/10 Javascript
js实现缓冲运动效果的方法
2015/04/10 Javascript
jQuery中hover与mouseover和mouseout的区别分析
2015/12/24 Javascript
js阻止浏览器默认行为触发的通用方法(推荐)
2016/05/15 Javascript
ThinkJS中如何使用MongoDB的CURD操作
2016/12/13 Javascript
Vue.js:使用Vue-Router 2实现路由功能介绍
2017/02/22 Javascript
jQuery插件zTree实现单独选中根节点中第一个节点示例
2017/03/08 Javascript
nodejs入门教程四:URL相关模块用法分析
2017/04/24 NodeJs
JS仿QQ好友列表展开、收缩功能(第一篇)
2017/07/07 Javascript
学习JS中的DOM节点以及操作
2018/04/30 Javascript
nodejs之koa2请求示例(GET,POST)
2018/08/07 NodeJs
详解vue-cli3 中跨域解决方案
2019/04/10 Javascript
深入学习Vue nextTick的用法及原理
2019/10/08 Javascript
Python的装饰器使用详解
2017/06/26 Python
轻松理解Python 中的 descriptor
2017/09/15 Python
python使用itchat库实现微信机器人(好友聊天、群聊天)
2018/01/04 Python
解决python selenium3启动不了firefox的问题
2018/10/13 Python
Pytorch训练过程出现nan的解决方式
2020/01/02 Python
什么是Python变量作用域
2020/06/03 Python
在python中对于bool布尔值的取反操作
2020/12/11 Python
HTML5在微信内置浏览器下右上角菜单的调整字体导致页面显示错乱的问题
2021/01/19 HTML / CSS
德国柯吉澳趣味家居:Koziol
2017/08/24 全球购物
大学生收银员求职信分享
2014/01/02 职场文书
家长会邀请书
2014/01/25 职场文书
公司采购主管岗位职责
2014/06/17 职场文书
花坛标语大全
2014/06/30 职场文书
如何写股份合作协议书
2014/09/11 职场文书
承诺函范文
2015/01/21 职场文书
英语辞职信范文
2015/02/28 职场文书
2015年宣传部个人工作总结
2015/05/14 职场文书
nginx配置ssl实现https的方法示例
2021/03/31 Servers