Javascript while循环,其中条件是一个承诺

时间:2017-05-04 10:20:10

标签: javascript promise

是否可以在条件为承诺的情况下创建本机JavaScript while循环?

编辑: 我尝试做的是在将文件上传到firebase存储之前执行检查,以查看firebase存储中是否已存在具有相同名称的文件。如果已存在具有相同名称的文件,则添加随机后缀并再次检查。

var storageRef = firebase.storage().ref().child(fileName);

while(storageRef.getDownloadURL()) {
    // create random number in between 0 and 100
    var random = Math.floor((Math.random() * 100) + 1);    
    storageRef = firebase.storage().ref().child(fileName + random);
}

storageRef.put(file);

2 个答案:

答案 0 :(得分:14)

  

是否有可能在条件为承诺的情况下进行原生JavaScript循环?

不,不是。

尝试这样做有几个问题:

  1. 使用ES6标准承诺,无法直接测试承诺的价值。对最终解析值的唯一访问权限是.then()。你不能while (p !== resolved)

  2. 即使你可以循环使用promises值,因为Javascript是事件驱动的和单线程的,如果你确实做了一个循环,那么promise的异步操作永远不会运行,并且承诺永远无法得到解决

  3. 相反,您只需使用:

    p.then(function(result) {
        // process result here
    }).catch(function(err) {
        // process error here
    });
    

    如果你想在循环中做更多的事情,你必须先披露实际的代码,然后我们才能进一步建议如何做到这一点。

    如果你想在某些条件下重复某些操作,那么只需将该操作放在一个函数中,在.then()处理程序中测试条件,如果你想重复,那么只需再次调用该函数。 p>

    function doSomething() {
        // some async operation that returns a promise
    }
    
    function next() {
        return doSomething.then(function(result) {
            if (result < someValue) {
                 // run the operation again
                 return next();
            } else {
                 return result;
            }
        });
    }
    
    next().then(function(result) {
          // process final result here
    }).catch(function(err) {
        // process error here
    });
    

    编辑:使用ES7,您可以使用asyncawait。它不会真的成为一个while循环,但它会消除对while循环的需要,因为你不必进行&#34; poll&#34;完全是异步值。

    async function f() {
       let value = await somePromise;
       // put code here to execute after the promise
       console.log(value);
    }
    

    函数f()的内部执行将暂停,直到promise解决或拒绝。请注意,f()的来电者不会被暂停。 f()行执行后,await会立即返回承诺。当f()的内部执行最终完成时,该承诺本身将解决并拒绝。

答案 1 :(得分:1)

是的!

您正在寻找的是生成器:https://developer.mozilla.org/en-US/docs/Web/JavaScript/Guide/Iterators_and_Generators

我更喜欢使用Observables e.g. RxJS来处理更复杂的事情。