Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Is Javascript event queue a simple FIFO or not?

Take a look at this example:

function A() { console.log('A'); }
function B() { console.log('B'); }
// and then i setTimeout(fn, 0) both of them
setTimeout(A, 0);
setTimeout(B, 0);

Is it guarantied that B will immediately run after A?
Is it possible that browser add another task in the queue between A and B?

note: none of A or B functions are adding any new tasks to event loop.

var callbacks = [];
// then add a bunch of callbacks ... (none adds events to event queue)
//case 1:
callbacks.forEach(cb => setTimeout(cb,0))
//case 2:
setTimeout(function() {
   callbacks.forEach(cb => cb());
},0);

Are there any difference in the order of execution of callbacks in case 1 vs case 2 ?

like image 450
Amin Roosta Avatar asked Feb 09 '16 16:02

Amin Roosta


3 Answers

Is it guarantied that B will immediately run after A?

Not immediately, no, but it's guaranteed that B will run after A. Full details in the spec, but in short, this is specifically addressed in the timer initialization steps which say in part:

Wait until any invocations of this algorithm that had the same method context, that started before this one, and whose timeout is equal to or less than this one's, have completed.

Optionally, wait a further user-agent defined length of time.

Queue the task task.

...where task is the task of calling the callback you gave setTimeout.

The task queue is required to be run in order, and so A will run before B on a compliant browser.

Note that this is guaranteed because they were queued by the same method context (see the spec for details of what that means).

Is it possible that browser add another task in the queue between A and B?

Yes. The browser can be multi-threaded and queue a task for some other thing (a message from a web worker, etc.) in-between queuing the tasks for A and B. In that case, you'd see A run, then your handler for the other task (processing the message from the web worker or whatever), then B.

like image 199
T.J. Crowder Avatar answered Sep 21 '22 14:09

T.J. Crowder


They will always fire in the correct order, A then B. However, they may not fire consecutively.

In fact, the specification says that timeout callbacks are not even placed on the execution queue until the timer has elapsed, which may be subject to additional delays - the timeout you specify is only a minimum amount of time to wait.

like image 40
James Thorpe Avatar answered Sep 19 '22 14:09

James Thorpe


JavaScript uses an event queue for timers.

enter image description here

Also see this article: Excellent and still actual article about timers in JavaScript by John Resig.

like image 38
Qbic Avatar answered Sep 21 '22 14:09

Qbic