异步javascript,promises链接 - 解析后没有执行函数[重复]

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

这个问题在这里已有答案:

我正在与承诺合作。当我链接promises时,最后一个then块不会被执行。所有其他块都被执行,但在最后一个承诺解决后没有任何反应。有人可以向我解释我错过了什么吗?

var x = 1;
$(document).ready(function() {
  getJobId(token).then(function(rsp) {
    return rsp;
  }).then(function(job_id) {
    looper().then(function(rsp) {
      console.log("app finished : " + rsp); // this block never gets called
    });
  });
});

function getJobId(token) {
  // does an API call that returns a promise
  return $.ajax({
    url: "url"
  });
}

function looper() {
  return new Promise(function(resolve, reject) {
    setTimeout(function() {
      // if the call is successful
      if (x == 5) {
        resolve(1); // returns the value 1
      } else {
        x++; // we increment the value of the counter
        console.log("not solved yet");
        looper(); // we call the same function again
      }
    }, 5000); // (waits for 5 seconds)
  });
}
javascript jquery asynchronous promise
1个回答
2
投票

问题是你永远不会解决你正在等待的承诺,这是looper返回的第一个承诺。

您必须始终解决或拒绝承诺,或使其依赖于另一个承诺。在这种情况下,做到这一点的最小变化是通过将后续looper中的promise传递给resolve来使先前的变量依赖于后者:

resolve(looper()); // we call the same function again

但那不是我要做的。相反,我不会让looper自称。我会直接处理它:

function looper() {
  function loop(resolve, reject) {
    setTimeout(function() {
      // if the call is successful
      if (x == 5) {
        resolve(1); // returns the value 1
      } else {
        x++; // we increment the value of the counter
        console.log("not solved yet");
        loop(resolve, reject);
      }
    }, 5000); // (waits for 5 seconds)
  }
  return new Promise(loop);
}

作为一个单独的问题,你不是在处理失败。这样做很重要。在这种情况下,可能会在looper.then处理程序中返回来自ready的promise并添加一个catch

var x = 1;
$(document).ready(function() {
  getJobId(token).then(function(rsp) {
    return rsp;
  }).then(function(job_id) {
    return looper().then(function(rsp) {
      console.log("app finished : " + rsp); // this block never gets called
    });
  }).catch(function(error) {
    // Handle/report error here
  });
});

function getJobId(token) {
  // does an API call that returns a promise
  return $.ajax({
    url: "url"
  });
}

function looper() {
  function loop(resolve, reject) {
    setTimeout(function() {
      // if the call is successful
      if (x == 5) {
        resolve(1); // returns the value 1
      } else {
        x++; // we increment the value of the counter
        console.log("not solved yet");
        loop(resolve, reject);
      }
    }, 5000); // (waits for 5 seconds)
  }
  return new Promise(loop);
}

旁注2:既然你正在使用Promise,我认为你的目标是现代环境。在这种情况下,您可以考虑使用fetch(返回原生承诺)而不是$.ajax,它返回一个jQuery jqXHR对象,它有点与Promise兼容。

© www.soinside.com 2019 - 2024. All rights reserved.