代码之家  ›  专栏  ›  技术社区  ›  Kraken

动态履行承诺。全部()

  •  1
  • Kraken  · 技术社区  · 8 年前

    我想知道为什么这段代码不起作用。我在一个依赖树(deepObject)中循环,对于每个依赖树,我都希望运行一个返回承诺的函数。然后我希望下一组函数在所有承诺解决之后发生,但是控制台在Promise.all中记录的日志没有执行。 ES6也很酷,如果您有更好的方法,但是我也很想知道为什么这段代码不能工作。

    更新以添加 .catch (这没有效果)

    for (let i = 0; i < keys.length; i++) {
        promisesArray.push(promiseFunction(deepObject[keys[i]]));
    }
    Promise.all(promisesArray).then(resolved => {
        console.log('dep promises resolved');
        console.log(`resolved: ${JSON.stringify(resolved)}`);
    }).catch(err => console.error(new Error(err));
    
    // promiseFunction is recursive
    promiseFunction(obj) {
        return new Promise((resolve, reject) => {
    
            const keys = Object.keys(deepObj);
            for (let j = 0; j < keys.length; j++) {
                if (Object.keys(deepObj[keys[j]]).length) {
                    // adding return statement to following line breaks it
                    // that was already recommended, see threads
                    promiseFunction(deepObj[keys[j]]);
                } else {
                    const dep = new Package(keys[j]);
                    console.log(`skan dep: ${keys[j]}`);
                    dep.fetch().then(() => {
                        return anotherFunction();
                    }).then(() => {
                        return Promise.all([
                            promise1(),
                            promise2(),
                            promise3(),
                        ]).then(resolved => {
                            if (resolved[0].propertyINeed) {
                                resolve(true);
                            }
                            resolve(false);
                        });
                    }).catch(err => {
                        console.error(new Error(err));
                        process.exit(1);
                    });
                }
            }
        });
    

    我知道这次谈话- has been discussed - on here before

    在上面的第二个链接中,接受的答案表明:

    如果您异步填充数组,您应该得到该数组的一个承诺,然后使用.then(promise.all.bind(promise))。如果你不知道什么时候你停止增加承诺,无论如何这是不可能的,因为它们可能永远都不会被解决。

    不过,我并没有使用Async填充数组。我需要这个吗?我这里缺什么?

    更新

    因为我现在在两个 .then() 以及 .catch() 似乎有什么事情出错了,与里面发生的事情无关。

    在前面添加RETURN语句 promiseFunction(deepObj[keys[j]]); 打破了递归。我从迭代173个对象到68个。添加catch没有记录其他结果。上面的代码被更新以共享更多的递归fn。当我运行它时,它似乎执行了所有的承诺,但我没有办法知道这一点。我最关心的是了解1。promise.all的promise数组包含它应该和2的所有对象。捕捉对递归对象内所有对象的所有承诺都已解决的时刻。

    另外,对于记录,返回承诺的每个函数都必须是异步的。为了简化和删除任何不必要的承诺,我已经多次重复这些内容。任务很复杂。必须执行一系列步骤,它们是异步的,并且它们是链接的,因为它们必须以特定的顺序进行解析。

    2 回复  |  直到 8 年前
        1
  •  2
  •   Quentin    8 年前
    if (Object.keys(obj[keys[j]]).length) {
        promiseFunction(obj[keys[j]]);
    } else {
        // and some more async hell that all resolves correctly
    

    如果 Object.keys(obj[keys[j]]).length true 那你就不打电话了 resolve reject 所以承诺永远不会实现。

    (注意呼叫 promiseFunction 递归地创建 新的 永不兑现的承诺 Promise.all )。

    因为你的一些承诺没有解决, 承诺。所有 也不会。


    你可能需要更多的东西:

    var promises = [];
    processObject(obj);
    Promise.all(promises).then(etc etc);
    
    function processObject(object) {
        for ( loop; over; object ) {
            if (condition) {
                 processObject(object[something]);
            } else {
                 promises.push(new Promise( (res, rej) => {
                     // so something async
                 });
            }
        }
    }
    
        2
  •  0
  •   Fabio Lolli    8 年前

    让我们看看你的 promiseFunction ……

    for (let j = 0; j < keys.length; j++) {
        if (Object.keys(obj[keys[j]]).length) {
            //if you get in here, promiseFunction returns undefined, and it never gets resolved
            promiseFunction(obj[keys[j]]);
        } else {
            const dep = new Package(keys[j]);
            console.log(`skan dep: ${keys[j]}`);
            // and some more async hell that all resolves correctly
            //but even if it resolves correctly, you still have the if...
        }
    }
    

    要想耍花招,就把你的 承诺功能 导致if语句:

    for (let j = 0; j < keys.length; j++) {
        if (Object.keys(obj[keys[j]]).length) {
            //if you get in here, you're saying this promise will depend on how this second promiseFunction will resolve
            return promiseFunction(obj[keys[j]]);
        } else {
            //omitted for brevity...
            resolve('your value');
        }
    }
    

    现在,当你进入国际单项体育联合会的声明时,你基本上是在告诉承诺,要根据第二个是否 承诺功能 已经正确解决了-你将把这个决议委托给另一个承诺。

    我从来没听过有人给它起这个名字,但你可以把它看作是承诺递归:)