This example confuse my understanding of how the node.js
works:
// 1.
numbers.forEach(function(number) {
queue.push(Q.call(slowFunction, this, number));
});
// 2.
// Q.all: execute an array of 'promises' and 'then' call either a resolve
// callback (fulfilled promises) or reject callback (rejected promises)
Q.all(queue).then(function(ful) {
// All the results from Q.all are on the argument as an array
console.log('fulfilled', ful);
}, function(rej) {
// The first rejected (error thrown) will be here only
console.log('rejected', rej);
}).fail(function(err) {
// If something went wrong, then we catch it here, usually when there is no
// rejected callback.
console.log('fail', err);
}).fin(function() {
// Finally statement; executed no matter of the above results
console.log('finally');
});
Why it is assumed here, that 1.
and 2.
parts of code will be executed sequentially?
So, where is the guarantee that Q.all(queue)
works on all queue
elements pushed in 1.
? Could it be so, that the numbers
from 1.
is so big, that it works than parallel to 2.
?
These ideas coming from the understanding that node.js will handling 1.
and 2.
first of all with the node.js event-loop
and then give it to workers
, which are actually analogue to the normal threads.
So the question - will be 1.
and 2.
executed parallel to each other, started from node.js event-loop
sequentially or will they be executed sequentially (the 1.
push all elements in the queue and only after that the 2.
starts to handling each element in the queue
) ?
Please provide arguments with some direct links to documentation for this topic.
At the topmost level, 1. and 2's Q.all(queue).then(...).fail(...).fin(...);
method chain, will unambiguously be executed sequentially.
The precise timing of execution of functions defined/called within 1 and 2 depends very much on the nature of slowFunction
.
If slowFunction
is performed wholly by synchronous javascript (eg. some extensive Math), then 1 will have completed in its entirety before 2 starts. In this case the callbacks specified in 2 will execute very shortly after 2's method chain has finished executing because any promises returned by slowfunction
will be (or at least should be) already resolved.
If however, slowFunction
involves one or more asynchronous node I/O process (eg. file handling or resource fetching), then each call to it will (at least in part) be undertaken by a non-blocking worker thread (not javascript); in this case, providing slowFunction
is correctly written, queue
will accumulate a set of promises, each of which will be resolved or rejected later. The callbacks specified in 2 will execute after 2's method chain has finished executing AND when all the promises have been either resolved or rejected.
For me, a rephrased version of 2's introductory text would go a long way toward explaining the order of execution :
Q.all: Wait for every 'promise' in the
queue
array of to be either resolved or rejected 'then' call the corresponding callback function.
Ref: http://rickgaribay.net/archive/2012/01/28/node-is-not-single-threaded.aspx