2016-10-14 54 views
0

我新的Javascript和做履带,我创建了4无极这些Promise.then(),但功能运行异步

var openConfig = new Promise((resolve, reject) => { 
    fs.readFile('./config.json', (err, data) => { 
    if (err) throw err; 
    config = JSON.parse(data); 
    client = new MsTranslator({ 
     client_id: config.translatorId, 
     client_secret: config.translatorSecret 
    }, true) 
    resolve(); 
    }) 
}) 

var openFile = new Promise((resolve, reject) => { 
    console.log('Opening file...') 
    fs.readFile('./writing/writing.json', (err, data) => { 
    if (err) throw err; 
    writing = JSON.parse(data); 
    console.log('Done parsing file'); 
    resolve(); 
    }) 
}) 

var ask = new Promise((resolve, reject) => { 
    var rl = readline.createInterface({ 
    input: process.stdin, 
    output: process.stdout 
    }) 
    rl.question('Which lesson do you want to add? ', (ans) => { 
    lessonId = ans; 
    rl.close(); 
    resolve(); 
    }) 
}) 

var createLesson = new Promise((resolve, reject) => { 
    console.log('Now processing lesson ' + lessonId); 
}) 

然后调用第一承诺

openConfig 
    .then(() => { 
    return openFile; 
    }) 
    .then(() => { 
    return ask; 
    }) 
    .then(() => { 
    return createLesson; 
    }) 

但当我运行,控制台显示

Opening file... 
Which lesson do you want to add? Now processing lesson undefined 
Done parsing file 

我明白我的承诺是错误的,我的功能运行异步。你能帮我解决这个问题吗?

谢谢。

+2

您正在创建承诺,您应该创建返回承诺的函数。 – Jeff

回答

0

不是指定新的承诺,以增值经销商(这些只要创建运行),你应该将它们包装成函数,这又回到了新的承诺的

为了帮助你了解这里是一个简单的例子:

function p1 (data) { 
    return new Promise(function (resolve, reject) { 
     resolve(Object.assign(data, {a:1})); 
    }); 
} 

function p2 (data) { 
    return new Promise(function (resolve, reject) { 
     resolve(Object.assign(data, {b:2})); 
    }); 
} 

function p3 (data) { 
    return new Promise(function (resolve, reject) { 
     resolve(Object.assign(data, {c:3})); 
    }); 
} 

p1({z:0}) 
.then(p2) 
.then(p3) 
.then((data)=>console.log(data)) 

这导致{ z: 0, a: 1, b: 2, c: 3 }

看到这里,如果你想实验一下上述:https://repl.it/DwNB/0


在一个单独的说明,如果您使用的承诺,还应该处理链中的错误在最后.catch(),而不是同步throw荷兰国际集团中途。这就是reject的回拨!

2

承诺不是“叫”。在您的then连锁店中,您只能按顺序等待它们 - 但是当您的创建了的承诺时,任务已经开始。如果你想排序的行动,把他们的功能。

顺便说一句,你的代码包含多个典型的错误。 Don't use global variables,始终promisify在尽可能低的水平:

function openFile(path) { 
    return new Promise((resolve, reject) => { 
    fs.readFile('./config.json', (err, data) => { 
     if (err) reject(err); // never `throw err` in non-promise callbacks! 
     else resolve(data); 
    }); 
    }); 
} 
function openJSON(path) { 
    return openFile(path).then(JSON.parse); 
} 
function openConfig(path) { 
    return openJSON(path).then(config => 
    new MsTranslator({ 
     client_id: config.translatorId, 
     client_secret: config.translatorSecret 
    }, true) 
) 
} 
function ask(question) { 
    return new Promise((resolve, reject) => { 
    var rl = readline.createInterface({ 
     input: process.stdin, 
     output: process.stdout 
    }) 
    rl.question(question, ans => { 
     rl.close(); 
     resolve(ans); // always resolve to *something* 
    }); 
    }); 
} 

readConfig('./config.json') 
.then(client => { 
    console.log('Opening file...') 
    return openJSON('./writing/writing.json'); 
}) 
.then(writing => { 
    console.log('Done parsing file'); 
    return ask('Which lesson do you want to add? '); 
}) 
.then(lessonId => { 
    console.log('Now processing lesson ' + lessonId); 
});