gpt4 book ai didi

node.js - 在单独的线程 Node Js 中运行长时间运行的快速 API 进程

转载 作者:搜寻专家 更新时间:2023-10-31 22:36:19 24 4
gpt4 key购买 nike

我有一个 API 调用大约需要 5-10 分钟来处理。我围绕它设置了一个超时方法,以便立即获得状态为已排队的 API 响应。

下面是简单的视觉效果

doWork(object) => { /*... Takes 5 minutes */ }

app.post('/longProcess',(req,res)=> {
setTimeout(this.doWork(req.body), 1000);
res.send({ status: 'queued' });
})

这适用于第一个立即响应的请求。但是第二个请求被锁定等待 doWork 完成。

我真正想做的不是使用 SetTimeout,而是将 longProcess 发送到一个单独的单线程,一个一个地排队和处理论文。

有什么建议吗?

最佳答案

问题

问题不在于 doWork() 花费了很多时间,而在于它显然会在整个生命周期内阻塞您的线程,并且不会让事件循环有任何运行的机会。

可能的原因

这可能是由多种原因引起的,我在这里只能猜测,因为您没有显示 doWork() 的来源,甚至没有描述它的作用和方式。例如:

  • 您的 doWork() 可能会使用诸如 fs.readFileSync() 之类的阻塞操作或名称中带有 Sync 的其他函数。
  • 您的 doWork() 可能有一个 forwhile 循环,它会旋转 5-10 分钟并在这样做时阻塞事件循环.
  • 您的代码进行了一些严肃的数字运算,没有分成多个步骤让事件循环在这些步骤之间滚动。

一般来说,如果您的 doWork() 不阻塞您的主线程,并且它不应该阻止其他连接获得服务,即使是一毫秒,它也可能需要数小时才能运行。

解决方案

停止阻塞线程

该问题最简单的解决方案可能是避免阻塞函数调用(那些带有 Sync 后缀或您自己的函数)、长时间运行的循环和没有分成短步骤的繁重计算。

例如:

  • 不要使用 readFileSync(),而是使用 readFile()
  • 不要使用长时间运行的 for/while 循环,而是使用 process.nextTick()
  • 不要使用非常深的递归(可能要归功于 TCO),而是使用通过 process.nextTick()
  • 分成多个部分的循环

如果无法应用上述解决方案(由于我对您的 doWork() 函数一无所知,所以我无从得知)那么您可以采取另一种方法。您还可以做一些其他事情。

产生一个进程

另一种解决方案是在每次启动长时间运行的任务时使用 child_process 生成不同的进程。当 child 结束工作并做出相应 react 时,您的主要流程可能会收到通知,但在等待时不会被阻止。请参阅:https://nodejs.org/api/child_process.html

使用队列

您还可以使用待处理作业队列并由其他进程处理它们,而不会影响您的主程序,该程序只会安排新任务而不执行或等待它们。通常像这样的队列是用 Redis 完成的,但也可以用 CouchDB 或 MongoDB 完成。您需要有一些挂起任务的中央注册表,您的工作进程可以从中获取它们。在 Node 中有很多模块可以做到这一点,例如:

请参阅这些模块的文档以了解哪一个最适合您的需求。

关于node.js - 在单独的线程 Node Js 中运行长时间运行的快速 API 进程,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/40085654/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com