【问题标题】:Waiting for promises inside the object to resolve等待对象内部的 Promise 解决
【发布时间】:2021-01-13 18:42:45
【问题描述】:

我有一个对象,它的值是 Promise。对象字段可以具有不同类型的值,例如函数、承诺、字符串、数字或其他对象。 如何实现一个等待对象中所有承诺解决的函数?

const asyncFunction = () => {
  return Promise.resolve("Resolved!")
}
const nonAsyncFunction = () => {
  return "Resolved!"
}
const awaitObjectWithPromise = (obj) => {
  // Returns a promise which waits for all
  // the promises inside "obj" to be resolved.
}
let obj = {
  key1: asyncFunction(),
  key2: nonAsyncFunction(),
  key3: "Some Value",
  parent1: {
    key1: asyncFunction(),
    key2: nonAsyncFunction(),
    key3: "Some Value"
  }
}

awaitObjectWithPromise(obj).then((obj) => {
  console.log(obj);
  // Should output:
  // {
  //     key1: "Resolved!",
  //     key2: "Resolved!",
  //     key3: "Some Value",
  //     parent1: {
  //         key1: "Resolved!",
  //         key2: "Resolved!",
  //         key3: "Some Value"
  //     }
  // }
})

【问题讨论】:

  • 我认为可以创建您需要的功能。等等,我正在努力。

标签: javascript async-await es6-promise


【解决方案1】:

您可以遍历对象的键并解决承诺。

const asyncFunction = () => {
  return Promise.resolve("Resolved!")
}
const nonAsyncFunction = () => {
  return "Resolved!"
}
const awaitObjectWithPromise = async(obj) => {
  for (let prop in obj) {
    // If the propriety has a 'then' function it's a Promise
    if (typeof obj[prop].then === 'function') {
      obj[prop] = await obj[prop];
    }
    if (typeof obj[prop] === 'object') {
      obj[prop] = await awaitObjectWithPromise(obj[prop]);
    }
  }
  return obj;
}

let obj = {
  key1: asyncFunction(),
  key2: nonAsyncFunction(),
  key3: "Some Value",
  parent1: {
    key1: asyncFunction(),
    key2: nonAsyncFunction(),
    key3: "Some Value"
  }
}

awaitObjectWithPromise(obj).then((obj) => {
  console.log(obj);
});

【讨论】:

  • await像您在此处所做的那样在循环中进行阻塞并且具有主要的性能缺陷
【解决方案2】:

在接受的答案中,我对某些事情不满意:

  • 如果其中一个字段是null 或undefined,则会引发错误;
  • 输入值不能是 Promise;
  • 等待 Promise 缺乏并行性;

为了解决这些问题,我更改了函数:

const promiseAll = async (obj) => {
    if (obj && typeof obj.then == 'function') obj = await obj;
    if (!obj || typeof obj != 'object') return obj;
    const forWaiting = [];
    Object.keys(obj).forEach(k => {
        if (obj[k] && typeof obj[k].then == 'function') forWaiting.push(obj[k].then(res => obj[k] = res));
        if (obj[k] && typeof obj[k] == 'object') forWaiting.push(promiseAll(obj[k]))
    });
    await Promise.all(forWaiting);
    return obj;
}

也许对某人有用。

【讨论】:

    猜你喜欢
    • 2021-09-08
    • 2020-06-23
    • 1970-01-01
    • 1970-01-01
    • 2021-05-19
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多