我正在开发一个 Web 应用程序,该应用程序将接收来自用户的请求,并且必须点击许多外部 API 来编写对该请求的答案。这可以直接从主网络线程使用 gevent 之类的东西来扇出请求来完成。
或者,我在想,我可以将传入的请求放入队列并使用工作人员来分配负载。这个想法是尽量保持实时,同时将请求分配给几个工作人员。这些工作人员中的每一个都将只查询众多外部 API 中的一个。然后,他们收到的响应将经过一系列转换,保存到数据库中,转换为通用模式并保存在通用数据库中,最终组合成一个大响应,该响应将通过 Web 请求返回。在用户等待的情况下,Web 请求很可能一直处于阻塞状态,因此尽可能快地保持排队和出队很重要。
外部 API 调用可以轻松转换为单独的任务。我认为从一个 api 任务到转换到数据库保存任务的链接可以使用链等来完成,并且最终结果结合所有结果使用和弦返回到 Web 线程。
一些问题:
- 这可以(并且应该)用芹菜来完成吗?
- 我正在使用django。我应该尝试在普通芹菜上使用 django-celery 吗?
- 这些任务中的每一项都可能衍生出其他任务——例如记录刚刚发生的事情或其他类型的分支。这可能吗?
- 任务是否可以返回他们获得的数据 - 即可能通过 celery 的数据(在这种情况下作为底层的 redis)或者他们应该写入数据库,并只是传递指向该数据的指针?
- 每个任务主要是 I/O 绑定的,最初只是要使用来自 web 线程的 gevent 来扇出请求并跳过整个队列设计,但事实证明它将被重用于不同的组件。试图通过 Qs 实时保持整个往返行程可能需要许多工作人员确保队列大部分是空的。或者是吗?运行 gevent 工作池会对此有所帮助吗?
- 我是否必须编写 gevent 特定任务或者使用 gevent 池自动处理网络 IO?
- 是否可以为某些任务分配优先级?
- 让它们井井有条呢?
- 我应该跳过芹菜而只使用kombu吗?
- 芹菜似乎更适合可以推迟且对时间不敏感的“任务”。我是不是想保持这个实时性?
- 我应该看哪些其他技术?
更新:试图对此进行更多讨论。我在 Kombu 上做了一些阅读,它似乎能够做我想做的事,尽管水平比 celery 低得多。这是我想到的图表。
Kombu 可访问的原始队列似乎有可能使许多工作人员能够订阅广播消息。如果使用队列,则发布者不需要知道类型和编号。可以使用 Celery 实现类似的功能吗?似乎如果你想制作和弦,你需要在运行时知道和弦中将涉及哪些任务,而在这种情况下,你可以简单地将听众添加到广播中,并简单地确保他们宣布他们在运行以将响应添加到最终队列。
更新2:我看到有广播的能力你能把它和和弦结合起来吗?一般来说,你能把芹菜和生海带结合起来吗?这听起来像是一个关于冰沙的问题。