保持nodejs请求等待直到第一个完成

时间:2018-08-20 06:50:25

标签: node.js

我遇到了nodejs api的情况。我要存档的是当同一用户同时点击相同的API时,我要阻止或排队他的第二个请求,直到第一个请求完成。 PS-我想将此应用到同一用户 预先感谢

2 个答案:

答案 0 :(得分:0)

您可以使用信号量来完成此操作。信号量将基于客户端,其中每个客户端在接收请求时只有一个信号量,服务器将通过锁定机制停止接收另一个请求,并且在响应后,应释放锁定。

演示

let clientSemaphores = {};
const semaphore = require('semaphore');
var server = require('http').createServer(function(req, res) {
  var client = req.url.split("/")[1];  //client id to specify
  console.log(client, " request recieved");
  if (!clientSemaphores[client] || clientSemaphores[client].current < clientSemaphores[client].capacity){
    clientSemaphores[client] = clientSemaphores[client] || semaphore(1);
    clientSemaphores[client].take(function() {
      setTimeout(() => {
        res.write(client + " Then good day, madam!\n");
        res.end(client + " We hope to see you soon for tea.");
        clientSemaphores[client].leave();
      }, 5000);
    });
  } else {
    res.end(client + " Request already processing... please wait...");
  }
});

server.listen(8000);

OR

HTTP管道

持久性HTTP允许我们重用多个应用程序请求之间的现有连接,但这意味着在客户端上执行严格的先进先出(FIFO)排队顺序:分派请求,等待完整响应,分派来自下一个请求的请求。客户队列。 HTTP管道传输是此工作流程的一个很小但重要的优化,它使我们能够将FIFO队列从客户端(请求队列)重定位到服务器(响应队列)。 参考:HTTP Pipelining

答案 1 :(得分:0)

如果应用程序既无状态又要在生产环境中横向扩展两个或多个副本,我不确定在服务器端执行任何操作(如信号灯)是否可以解决此问题。

  • 所有Pod(应用服务器)必须针对使用的端点保持相同的信号量值
  • 我认为您可以使用数据库标志实现相同的机制,也可以使用Redis指示其中一台应用服务器上的操作正在进行中。
  • 根据客户的请求,与进行会话(就保持某种状态而言)一样好
  • 如果该端点执行的操作失败或使线程崩溃,您还将需要一种恢复机制来重置信号量。