对于轮询其他 API 的 API,我应该使用任务队列(Celery)、asyncio 还是两者都不使用?

Should I use a task queue (Celery), ayncio or neither for an API that polls other APIs?

我用 Django 写了一个 API ,目的是作为网站后端和我们使用的外部服务之间的桥梁,这样网站就不必处理很多外部请求APIs(CRM、日历事件、电子邮件提供商等)。

API主要是轮询其他服务,解析结果转发给网站后台。

我最初选择了基于 Celery 的任务队列,因为在我看来它是将处理卸载到另一个实例的正确工具,但我开始认为它并不真正符合目的。

由于网站期望同步响应,我的代码包含很多:

results = my_task.delay().get()

results = chain(fetch_results.s(), parse_results.s()).delay().get()

感觉这不是使用 Celery 任务的正确方法。

在拉取几十个请求并并行处理结果时效率很高——例如一个周期性的 刷新 任务——但为简单请求增加了很多开销(获取 - 解析- 转发),代表大部分流量。

我是否应该为那些 "simple requests" 完全同步并为特定场景保留 Celery 任务?是否有更适合我的 API 目的的替代设计(可能涉及 asyncio)?


在 EBS EC2 实例上使用 Django、Celery(带 Amazon SQS)。

您可以考虑将 Gevent 与您的 Django 网络服务器一起使用,以允许它针对您提到的 "simple requests" 高效运行而不会被阻止。如果继续使用这种方法,请确保将数据库连接与 PgBouncer 或 Pgpool-II 或 Python 库合并,因为每个 greenlet 都会建立自己的连接。

一旦你实现了它,也可以使用 Gevent 而不是 Celery 来处理异步处理,方法是加入多个 Greenlets,每个 Greenlets 都发出一个外部 API 请求,而不是产生传递消息的开销给外部芹菜工人。

您的实施与我们在 Kloudless 所做的类似,后者提供单个 API 来访问多个其他 API,包括 CRM、日历、存储等.