celery能否协同运行协同程序作为有状态/可恢复的任务?

2024-04-23 18:56:54 发布

您现在位置:Python中文网/ 问答频道 /正文

我目前正在调查芹菜在视频处理后端的使用。基本上我的问题是:

  1. 我有一个前端web服务器,可以同时处理大量的视频流(大约数千个)。在
  2. 每个流必须独立处理并并行处理。在
  3. 流处理可分为两种类型的操作:
    1. 逐帧操作(不需要有关前一帧或下一帧的信息的计算)
    2. 流级操作(对有序相邻帧的子集进行的计算)

给出第3点,我需要在整个过程中维护和更新框架的有序结构,并向芹菜工人计算该结构的子部分。最初,我想把事情安排如下:

[frontend server]  -stream-> [celery worker 1 (greenlet)] --> [celery worker 2 (prefork)]

其思想是,celery worker 1执行长期运行的任务,这些任务主要是I/O绑定的。本质上,这些任务将执行以下操作:

  1. 从前端服务器读取帧
  2. 从帧的base64表示中解码
  3. 将它放入前面提到的有序数据结构中(当前是collections.deque对象)。在

任何占用CPU的操作(图像分析)都被发送到celery worker 2。在

我的问题是:

我想将协同程序作为一个任务来执行,这样我就有了一个长时间运行的任务,我可以yield,这样就不会阻止celery worker 1的操作。换句话说,我希望能够做一些类似于:

^{pr2}$

有没有一种方法可以让基于协程的任务无限期地运行,理想情况下会产生结果,因为它们是{}生成的?


Tags: 服务器框架web信息类型视频过程结构
1条回答
网友
1楼 · 发布于 2024-04-23 18:56:54

Eventlet背后的主要思想是您希望编写同步代码,就像线程一样,socket.recv()应该在下一个语句之前阻塞当前线程。这种风格在调试时非常容易阅读、维护和推理。为了使事情变得有效和可伸缩,Eventlet在幕后魔术般地用绿色线程和epoll/kqueue/etc机制替换看似阻塞的代码,以便在适当的时间唤醒这些绿色线程。在

因此,您所需要的就是尽快执行eventlet.monkey_patch(),并确保在MyInputThingy中使用纯Python套接字操作。忘掉异步,只需像使用线程一样编写普通的阻塞代码。在

Eventlet使同步代码再次成为好代码。在

相关问题 更多 >