Reputation: 109
i want to create a fake discussion in JS with promises.
console.log wait X seconds,
console.log wait X seconds ...
Here is my code:
var addMessage = function (msg) {
return new Promise(function (resolve, reject) {
setTimeout( function() {
console.log(msg)
resolve()
}, 2500)
})
}
var scenario = function() {
addMessage('Hello who are you ?')
.then(addMessage('Hello I am John'))
.then(addMessage('Nice too meet you'))
.then(addMessage('Me too'))
.then(addMessage('Good Bye'))
.then(addMessage('Bye'))
}
scenario()
But with this code all console.log() are made at the same time (after 2500ms), i'm new with promises and i really don't master them.
Thank you !
Upvotes: 2
Views: 268
Reputation: 9261
Thomas has summed it up pretty well in his comment:
then() expects a function, but addMessage() returns a Promise. A Promise ain't a function. And, all your Promises are created at the same time, that's why they fire at the same time
You are constructing all the new Promises at the same time so they will immediately execute and the timers will then also simultaneously end at the same time as well. To mitigate this you can wrap addMessage
in a function inside of the .then
calls.
addMessage('Hello who are you ?')
.then(function () { addMessage('Hello I am John') })
.then(function () { addMessage('Nice too meet you') })
.then(function () { addMessage('Me too') })
.then(function () { addMessage('Good Bye') })
.then(function () { addMessage('Bye') })
Alternatively you could also use Function.prototype.bind() to avoid having to write an anonymous function each time.
addMessage('Hello who are you ?')
.then(addMessage.bind(null, 'Hello I am John'))
.then(addMessage.bind(null, 'Nice too meet you'))
.then(addMessage.bind(null, 'Me too'))
.then(addMessage.bind(null, 'Good Bye'))
.then(addMessage.bind(null, 'Bye'))
And of course if your environment is running a recent version of JavaScript you could also use arrow functions:
addMessage('Hello who are you ?')
.then(() => addMessage('Hello I am John'))
.then(() => addMessage('Nice too meet you'))
.then(() => addMessage('Me too'))
.then(() => addMessage('Good Bye'))
.then(() => addMessage('Bye'))
In the near future you will also be able to use the await keyword which eliminates the need for any .then
calls entirely:
await addMessage('Hello who are you ?')
await addMessage('Hello I am John')
await addMessage('Nice too meet you')
await addMessage('Me too')
await addMessage('Good Bye')
await addMessage('Bye')
Upvotes: 5