ICode9

精准搜索请尝试: 精确搜索
首页 > 编程语言> 文章详细

JavaScript 在 Promise.then 方法里返回新的 Promise

2022-08-12 22:04:10  阅读:196  来源: 互联网

标签:返回 resolve chaining JavaScript js promise loadScript Promise article


看一个实际的例子:

loadScript("/article/promise-chaining/one.js")
  .then(function(script) {
    return loadScript("/article/promise-chaining/two.js");
  })
  .then(function(script) {
    return loadScript("/article/promise-chaining/three.js");
  })
  .then(function(script) {
    // use functions declared in scripts
    // to show that they indeed loaded
    one();
    two();
    three();
  });

按照先后顺序,依次加载 one.js, two.js, three.js

当然也可以使用箭头函数的语法:

loadScript("/article/promise-chaining/one.js")
  .then(script => loadScript("/article/promise-chaining/two.js"))
  .then(script => loadScript("/article/promise-chaining/three.js"))
  .then(script => {
    // scripts are loaded, we can use functions declared there
    one();
    two();
    three();
  });

这里每个 loadScript 调用,都会返回一个 promise,这个新的 promise,在其被 resolve 时,会触发下一个 .then 的执行。

于是它开始加载下一个脚本。 所以脚本一个接一个地加载。

我们可以向链中添加更多异步操作。 请注意,代码仍然是 flat 的——它向下增长,而不是向右增长。

这种方式没有 pyramid of doom 的迹象。

虽然我们可以在 then 后面直接调用 loadScript:

loadScript("/article/promise-chaining/one.js").then(script1 => {
  loadScript("/article/promise-chaining/two.js").then(script2 => {
    loadScript("/article/promise-chaining/three.js").then(script3 => {
      // this function has access to variables script1, script2 and script3
      one();
      two();
      three();
    });
  });
});

此代码的作用相同:依次加载 3 个脚本。 但它 向右增长, 所以本质上仍然有回调地狱的问题。

Thenables 对象

准确地说,then 处理程序可能返回的不完全是一个 Promise,而是一个所谓的 thenable 对象——一个具有 .then 方法的任意 JavaScript 对象。 它将被视为与 Promise 相同的方式被处理。

这个想法是第 3 方库可以实现自己的 promise-compatible 对象。 它们可以有一组扩展的方法,但也可以与原生 Promise 兼容,因为它们实现了 .then。

看一个例子:

class Thenable {
  constructor(num) {
    this.num = num;
  }
  then(resolve, reject) {
    alert(resolve); // function() { native code }
    // resolve with this.num*2 after the 1 second
    setTimeout(() => resolve(this.num * 2), 1000); // (**)
  }
}

new Promise(resolve => resolve(1))
  .then(result => {
    return new Thenable(result); // (*)
  })
  .then(alert); // shows 2 after 1000ms

单步调试:

  1. 14 行 new Promise 内部的 executor 得到执行,立即 resolve,抛出 result 1

  1. 这会导致代码第 15 行 then 里的函数立即被调用,输入参数为 1,构造一个新的 Thenable 对象。

JavaScript 在第 16 行中检查 .then 处理程序返回的对象:如果它有一个名为 then 的可调用方法,那么它调用该 then 方法,并提供本地函数 resolve、reject 作为参数(类似于执行程序)并等待其中一个被调用。 在上面的示例中,resolve(2) 在 1 秒 (**) 后被调用。然后将结果进一步向下传递。

因此,下图第 16 行代码单步调试之后,会自动进入代码第 8 行。

  1. 打印出 resolve 原生函数的 native code 字符串。

  1. 代码第 10 行的 resolve,会触发第 18 行第二个 then 方法:

标签:返回,resolve,chaining,JavaScript,js,promise,loadScript,Promise,article
来源: https://www.cnblogs.com/sap-jerry/p/16581479.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有