Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

What exactly is a Node.js event loop tick?

I've been getting more into the internals of the Node.js architecture, and a term I see coming up a lot is "tick" as in "next tick of the event loop" or the function nextTick().

What I haven't seen is a solid definition of what exactly a "tick" is. Based on various articles (such as this one), I've been able to piece a concept together in my head, but I'm not sure how accurate it is.

Can I get a precise and detailed description of a Node.js event loop tick?

like image 317
d512 Avatar asked Nov 06 '13 20:11

d512


People also ask

What is tick of node JS event loop?

In Node. js, each iteration of an Event Loop is called a tick. To schedule a callback function to be invoked in the next iteration of the Event Loop, we use process.

What is event loop in JS?

JavaScript has a runtime model based on an event loop, which is responsible for executing the code, collecting and processing events, and executing queued sub-tasks. This model is quite different from models in other languages like C and Java.

What is meant by event loop?

In computer science, the event loop is a programming construct or design pattern that waits for and dispatches events or messages in a program.

Is node js event loop single threaded?

Event Loop uses Single Thread only. It is main heart of Node JS Platform Processing Model. Even Loop checks any Client Request is placed in Event Queue.


2 Answers

Remember that while JavaScript is single-threaded, all of node's I/O and calls to native APIs are either asynchronous (using platform-specific mechanisms), or run on a separate thread. (This is all handled through libuv.)

So when there's data available on a socket or a native API function has returned, we need a synchronized way to invoke the JavaScript function that is interested in the particular event that just happened.

It's not safe to just call the JS function from the thread where the native event happened for the same reasons that you'd encounter in a regular multi-threaded application – race conditions, non-atomic memory access, and so forth.

So what we do is place the event on a queue in a thread-safe manner. In oversimplified psuedocode, something like:

lock (queue) {     queue.push(event); } 

Then, back on the main JavaScript thread (but on the C side of things), we do something like:

while (true) {     // this is the beginning of a tick      lock (queue) {         var tickEvents = copy(queue); // copy the current queue items into thread-local memory         queue.empty(); // ..and empty out the shared queue     }      for (var i = 0; i < tickEvents.length; i++) {         InvokeJSFunction(tickEvents[i]);     }      // this the end of the tick } 

The while (true) (which doesn't actually exist in node's source code; this is purely illustrative) represents the event loop. The inner for invokes the JS function for each event that was on the queue.

This is a tick: the synchronous invocation of zero or more callback functions associated with any external events. Once the queue is emptied out and the last function returns, the tick is over. We go back to the beginning (the next tick) and check for events that were added to the queue from other threads while our JavaScript was running.

What can add things to the queue?

  • process.nextTick
  • setTimeout/setInterval
  • I/O (stuff from fs, net, and so forth)
  • crypto's processor-intensive functions like crypto streams, pbkdf2, and the PRNG (which are actually an example of...)
  • any native modules that use the libuv work queue to make synchronous C/C++ library calls look asynchronous
like image 63
josh3736 Avatar answered Oct 02 '22 16:10

josh3736


A simpler answer for those new to JavaScript:

The first thing to understand is that JavaScript is a "single-threaded environment". This refers to JavaScript's behavior of executing your blocks of code one at a time from "the event loop" on a single thread. Below there's a rudimentary implemenation of the event loop taken from Kyle Simpson's book ydkJS and afterwards, an explanation:

// `eventLoop` is an array that acts as a queue (first-in, first-out) var eventLoop = [ ]; var event;  // keep going "forever" while (true) {     // perform a "tick"     if (eventLoop.length > 0) {         // get the next event in the queue         event = eventLoop.shift();          // now, execute the next event         try {             event();         }         catch (err) {             reportError(err);         }     } } 

The first while loop simulates the event loop. A tick is the dequeuing of an event from the "event loop queue" and the execution of said event.

Please see the response of 'Josh3796' for a more detailed explanation of what happens in the dequeuing and execution of an event.

Also, I recommend reading Kyle Simpson's book for those who are interested in getting a deep understanding of JavaScript. It's completely free and open-source and can be found at this link: https://github.com/getify/You-Dont-Know-JS

The specific section I referenced can be found here: https://github.com/getify/You-Dont-Know-JS/blob/2nd-ed/sync-async/ch1.md

like image 30
Parm Avatar answered Oct 02 '22 17:10

Parm