JavaScript 异步/等待轮询以获取状态 - 函数未返回正确的数据

问题描述 投票:0回答:2

Context:Django 中使用 Celery 和 Redis 的异步任务管理。

我有一个在 Ajax 中发送 POST 请求的函数。服务器返回一个任务id。

使用任务 ID,我在 POST 请求之后启动另一个函数来获取任务状态,以检查工作人员是否已成功执行任务。

问题:我成功使用 JavaScript 进行轮询并记录结果。但最后我的函数没有返回正确的数据(if 语句中的数据)。就好像 if 语句返回的对象被忽略了。

我第一次写这样的函数。任何帮助将不胜感激🙏

代码

function cancelSimcard() {
  const cancellationLink = document.getElementById("cancellationLink");

  return {
    notificationOpen: false,
    message: "à remplacer",

    async sendCancellationRequest() {
      const data = await fetch(cancellationLink.dataset.url, {
        method: "POST",
      });
      const result = await data.json();
      const status = await getStatus(result.task_id);
    },
  };

  async function getStatus(task_id) {
    const statusData = await fetch(`/parc/task_status/${task_id}`, {
      method: "GET",
    });
    const statusResult = await statusData.json();

    if (statusResult.task_status === "SUCCESS") {
      console.log("DATA FROM SUCCESS BLOCK", statusResult);
      return statusResult;
    } else {
      await new Promise((resolve) => setTimeout(resolve, 1000));
      await getStatus(statusResult.task_id);
    }
    console.log("DATA AT THE END", statusResult);
  }
}

控制台结果:

**我试图从 success 块中获取数据以将其传递到 sendCancellationRequest() 函数中。 **

javascript django async-await fetch celery
2个回答
0
投票

正在进行递归调用,但结果没有像注释中提到的那样返回到原始调用者,因此,您需要确保正确返回递归调用的结果:

function cancelSimcard() {
  const cancellationLink = document.getElementById("cancellationLink");

  return {
    notificationOpen: false,
    message: "à remplacer",

    async sendCancellationRequest() {
      const data = await fetch(cancellationLink.dataset.url, {
        method: "POST",
      });
      const result = await data.json();
      const status = await getStatus(result.task_id);
      return status; // return the final status back
    },
  };

  async function getStatus(task_id) {
    const statusData = await fetch(`/parc/task_status/${task_id}`, {
      method: "GET",
    });
    const statusResult = await statusData.json();

    if (statusResult.task_status === "SUCCESS") {
      console.log("DATA FROM SUCCESS BLOCK", statusResult);
      return statusResult;
    } else {
      await new Promise((resolve) => setTimeout(resolve, 1000));
      let finalResultesult = await getStatus(statusResult.task_id); 
      return finalResultesult // return the result 
    }
  }
}

0
投票

您的

getStatus
函数在执行
else
块时不会返回任何内容,因此它返回
undefined
。换句话说,无论
getStatus
的递归调用返回什么,它都会被忽略,并返回
undefined

这种轮询可以用循环而不是递归来实现,这样就降低了犯此类错误的可能性:

  // Define this once for all:
  const delay = ms => new Promise((resolve) => setTimeout(resolve, ms));

  async function getStatus(task_id) {
    while (true) { // Loop
      const statusData = await fetch(`/parc/task_status/${task_id}`, {
        method: "GET",
      });
      const statusResult = await statusData.json();
      if (statusResult.task_status === "SUCCESS") {
        console.log("DATA FROM SUCCESS BLOCK", statusResult);
        return statusResult;
      }
      await delay(1000);
    }
  }
© www.soinside.com 2019 - 2024. All rights reserved.