Javascript 失言

Javascript 失言,javascript,node.js,express,promise,Javascript,Node.js,Express,Promise,我有一个承诺嵌套在另一个承诺中,如下所示: adb.screencap(list, id).then(function(missing) { adb.getScreens(list, id).then(function () { res.render('screencap', {output: "Screens captured."}) }) }) 其中adb.screencap和adb.getScreens为: adb.screencap = fun

我有一个承诺嵌套在另一个承诺中,如下所示:

 adb.screencap(list, id).then(function(missing) {
     adb.getScreens(list, id).then(function () {
         res.render('screencap', {output: "Screens captured."})
     })
 })
其中adb.screencap和adb.getScreens为:

adb.screencap = function(list, id){
    return new Promise(function (resolve, reject) {
        var array = new Array();
        var promises = new Array();

        for (var i = 0; i < list.length; i++) {
            var cmd = "adb -s " + list[i] + " shell screencap /sdcard/" + list[i] + "-" + id + ".png";
            var missing = new Array();

            console.log("== " + cmd);
            promises.push(adb.openArray(i, array, list, cmd, missing));
        }
        Promise.all(promises).then(function (missing) {
            console.log(("resolve"));
            resolve(missing);
        })
    })
}
adb.getScreens = function(list, id){
    return new Promise(function (resolve, reject){
        for (var i = 0; i < list.length; i++) {
            var cmd = 'adb -s ' + list[i] + ' pull /sdcard/' + list[i] + "-" + id + ".png /home/IdeaProjects/DeviceServer/public/files/" + list[i] + "-" + id + ".png";
            exec(cmd, function (err, stdout, stderr) {
                console.log(stdout);
                console.log(cmd);
            });
        }
        resolve();
    })
}
adb.screencap=函数(列表,id){
返回新承诺(功能(解决、拒绝){
var数组=新数组();
var=newarray();
对于(变量i=0;i

为什么在adb.screencap承诺之前完成adb.getScreens承诺?

您的
adb.openArray
是否返回承诺?那么只有
承诺。所有的
都会起作用


如果
exec
,您应该在回调中解决
getScreens
的承诺。它在外部,不等待exec完成。

您的
adb.openArray
是否承诺返回?那么只有
承诺。所有的
都会起作用


如果
exec
,您应该在回调中解决
getScreens
的承诺。它在外面,并不等待exec完成。

我仍在试图找出哪里出了问题,因为发生这种情况似乎很奇怪。 它可能位于openArray()方法或exec()函数中的某个位置

正如Felix所建议的,你可以简化一些事情:

// If the getScreens handler doesn't need the 'missing' returned from screencap
adb.screencap(list, id).then(function(missing) {
    return adb.getScreens(list, id);
}).then(function ( gottenScreens ) {
    res.render('screencap', {output: "Screens captured."})
});

// You can just return the Promise.all here instead of adding another promise
// just to resolve the outer one.
adb.screencap = function(list, id) {
    var array = new Array();
    var promises = new Array();
    for (var i = 0; i < list.length; i++) {
        var cmd = "adb -s " + list[i] + " shell screencap /sdcard/" + list[i] + "-" + id + ".png";
        var missing = new Array();

        console.log("== " + cmd);
        // is this some async operation or are you just creating all the commands here?
        // if so, it does't make sense to use a promise here.
        promises.push(adb.openArray(i, array, list, cmd, missing));
    }       
    return Promise.all(promises);
}
//如果getScreens处理程序不需要screencap返回的“missing”
adb.screencap(列表,id)。然后(函数(缺失){
返回adb.getScreens(列表,id);
}).then(函数(gottenScreens){
res.render('screencap',{output:'Screens capture.})
});
//你可以把承诺都还给我,而不是再加一个承诺
//只是为了解决外部问题。
adb.screencap=函数(列表,id){
var数组=新数组();
var=newarray();
对于(变量i=0;i
我仍在试图找出哪里出了问题,因为发生这种情况似乎很奇怪。 它可能位于openArray()方法或exec()函数中的某个位置

正如Felix所建议的,你可以简化一些事情:

// If the getScreens handler doesn't need the 'missing' returned from screencap
adb.screencap(list, id).then(function(missing) {
    return adb.getScreens(list, id);
}).then(function ( gottenScreens ) {
    res.render('screencap', {output: "Screens captured."})
});

// You can just return the Promise.all here instead of adding another promise
// just to resolve the outer one.
adb.screencap = function(list, id) {
    var array = new Array();
    var promises = new Array();
    for (var i = 0; i < list.length; i++) {
        var cmd = "adb -s " + list[i] + " shell screencap /sdcard/" + list[i] + "-" + id + ".png";
        var missing = new Array();

        console.log("== " + cmd);
        // is this some async operation or are you just creating all the commands here?
        // if so, it does't make sense to use a promise here.
        promises.push(adb.openArray(i, array, list, cmd, missing));
    }       
    return Promise.all(promises);
}
//如果getScreens处理程序不需要screencap返回的“missing”
adb.screencap(列表,id)。然后(函数(缺失){
返回adb.getScreens(列表,id);
}).then(函数(gottenScreens){
res.render('screencap',{output:'Screens capture.})
});
//你可以把承诺都还给我,而不是再加一个承诺
//只是为了解决外部问题。
adb.screencap=函数(列表,id){
var数组=新数组();
var=newarray();
对于(变量i=0;i
在内部的任何
exec()
调用完成之前,您正在解析
getScreens()
。它们是异步的。它们会在稍后完成,但您在启动它们之后立即调用
resolve()
。因此,您最终尝试在需要渲染的任何结果可用之前进行渲染

相反,您需要提示
exec()
本身,然后在数组中收集这些承诺,并使用
Promise.all()
查看所有承诺何时完成。只有这样才能真正完成
getScreens()

这里还有很多其他问题
screencap()
正在使用反模式。没有必要在这里创造你自己的承诺。您只需从
promise.all()
返回承诺,使用此反模式会导致您丢失任何承诺引发的错误

这里有一个建议:

// promisify exec
function execP(cmd) {
    return new Promise(function(resolve, reject) {
        exec(cmd, function(err, stdout, stderr) {
            if (err) return reject(err);
            console.log(cmd);
            console.log(stdout);
            console.log(stderr);
            resolve({stdout: stdout, stderr: stderr});
        });
    });
}

adb.getScreens = function(list, id){
    return Promise.all(list.map(function(item) {
       var cmd = 'adb -s ' + item + ' pull /sdcard/' + item + "-" + id + ".png /home/IdeaProjects/DeviceServer/public/files/" + item + "-" + id + ".png";
       return execP(cmd);
    }));
}
现在,
.getScreens()
返回一个承诺,该承诺只有在所有
exec()
调用完成后才会得到解决(这样,您的输出文件将可用并准备就绪,可供编辑使用)


这将
.getScreens()
配置为解析为包含所有exec调用中的stdout、stderr信息的对象数组。看起来您并没有试图使用该输出,但这是如何配置的。

您正在解析
getScreens()
,但其中的任何
exec()
调用尚未完成。它们是异步的。它们会在稍后完成,但您在启动它们之后立即调用
resolve()
。因此,您最终尝试在任何