Rectangle 27 77

The Node.js event loop runs under a single thread, this means the application code you write is evaluated on a single thread. Nodejs itself uses many threads underneath through libuv, but you never have to deal with with those when writing nodejs code.

Every call that involves I/O call requires you to register a callback. This call also returns immediately, this allows you to do multiple IO operations in parallel without using threads in your application code. As soon as an I/O operation is completed it's callback will be pushed on the event loop. It will be executed as soon as all the other callbacks that where pushed on the event loop before it are executed.

There are a few methods to do basic manipulation of how callbacks are added to the event loop. Usually you shouldn't need these, but every now and then they can be useful.

At no point will there ever be two true parallel paths of execution, so all operations are inherently thread safe. There usually will be several asynchronous concurrent paths of execution that are being managed by the event loop.

Because of the event loop, node doesn't have to start a new thread for every incoming tcp connection. This allows node to service hundreds of thousands of requests concurrently , as long as you aren't calculating the first 1000 prime numbers for each request.

This also means it's important to not do CPU intensive operations, as these will keep a lock on the event loop and prevent other asynchronous paths of execution from continuing. It's also important to not use the sync variant of all the I/O methods, as these will keep a lock on the event loop as well.

If you want to do CPU heavy things you should ether delegate it to a different process that can execute the CPU bound operation more efficiently or you could write it as a node native add on.

In order to manage writing many callbacks you will probably want to use a control flow library. I believe this is currently the most popular callback based library:

I've used callbacks and they pretty much drove me crazy, I've had much better experience using Promises, bluebird is a very popular and fast promise library:

I've found this to be a pretty sensitive topic in the node community (callbacks vs promises), so by all means, use what you feel will work best for you personally. A good control flow library should also give you async stack traces, this is really important for debugging.

The Node.js process will finish when the last callback in the event loop finishes it's path of execution and doesn't register any other callbacks.

This is not a complete explanation, I advice you to check out the following thread, it's pretty up to date:

@WillemD'haeseleer please! Explain me the next your phrase "The Node.js event loop runs under a single thread.. Nodejs itself uses many threads underneath trough libuv". I know how works js-loop in browser, but I do not understand what is the role of multi-threaded libuv.

threads are used by libuv for all sorts of stuff that required CPU bound operations. If you want to better understand that I recommend you read up on libuv here nikhilm.github.io/uvbook/threads.html, and here: nikhilm.github.io/uvbook/basics.html

How is nodejs able to manage concurrent connections? Does it do with a significant lag? I hear that it could support tens of thousands of concurrent connections, more than apache. Could you explain how all this is possible, provided nodejs handles/processes HTTP requests on a single thread?

"Every call that involves I/O call requires you to register a callback." That is not accurate. Calls like readFileSync, writeFileSync, etc do not require callbacks for I/O.

Node.js Event loop - Stack Overflow

node.js loops events
Rectangle 27 77

The Node.js event loop runs under a single thread, this means the application code you write is evaluated on a single thread. Nodejs itself uses many threads underneath through libuv, but you never have to deal with with those when writing nodejs code.

Every call that involves I/O call requires you to register a callback. This call also returns immediately, this allows you to do multiple IO operations in parallel without using threads in your application code. As soon as an I/O operation is completed it's callback will be pushed on the event loop. It will be executed as soon as all the other callbacks that where pushed on the event loop before it are executed.

There are a few methods to do basic manipulation of how callbacks are added to the event loop. Usually you shouldn't need these, but every now and then they can be useful.

At no point will there ever be two true parallel paths of execution, so all operations are inherently thread safe. There usually will be several asynchronous concurrent paths of execution that are being managed by the event loop.

Because of the event loop, node doesn't have to start a new thread for every incoming tcp connection. This allows node to service hundreds of thousands of requests concurrently , as long as you aren't calculating the first 1000 prime numbers for each request.

This also means it's important to not do CPU intensive operations, as these will keep a lock on the event loop and prevent other asynchronous paths of execution from continuing. It's also important to not use the sync variant of all the I/O methods, as these will keep a lock on the event loop as well.

If you want to do CPU heavy things you should ether delegate it to a different process that can execute the CPU bound operation more efficiently or you could write it as a node native add on.

In order to manage writing many callbacks you will probably want to use a control flow library. I believe this is currently the most popular callback based library:

I've used callbacks and they pretty much drove me crazy, I've had much better experience using Promises, bluebird is a very popular and fast promise library:

I've found this to be a pretty sensitive topic in the node community (callbacks vs promises), so by all means, use what you feel will work best for you personally. A good control flow library should also give you async stack traces, this is really important for debugging.

The Node.js process will finish when the last callback in the event loop finishes it's path of execution and doesn't register any other callbacks.

This is not a complete explanation, I advice you to check out the following thread, it's pretty up to date:

@WillemD'haeseleer please! Explain me the next your phrase "The Node.js event loop runs under a single thread.. Nodejs itself uses many threads underneath trough libuv". I know how works js-loop in browser, but I do not understand what is the role of multi-threaded libuv.

threads are used by libuv for all sorts of stuff that required CPU bound operations. If you want to better understand that I recommend you read up on libuv here nikhilm.github.io/uvbook/threads.html, and here: nikhilm.github.io/uvbook/basics.html

How is nodejs able to manage concurrent connections? Does it do with a significant lag? I hear that it could support tens of thousands of concurrent connections, more than apache. Could you explain how all this is possible, provided nodejs handles/processes HTTP requests on a single thread?

"Every call that involves I/O call requires you to register a callback." That is not accurate. Calls like readFileSync, writeFileSync, etc do not require callbacks for I/O.

Node.js Event loop - Stack Overflow

node.js loops events
Rectangle 27 18

The Node.js event loop runs under a single thread. Every I/O call requires you to register a callback. Every I/O call also returns immediately, this allows you to do multiple IO operations in parallel without using threads.

I would like to start explaining with this above quote, which is one of the common misunderstandings of node js framework that I am seeing everywhere.

Node.js does not magically handle all those asynchronous calls with just one thread and still keep that thread unblocked. It internally uses google's V8 engine and a library called libuv(written in c++) that enables it to delegate some potential asynchronous work to other worker threads (kind of like a pool of threads waiting there for any work to be delegated from the master node thread). Then later when those threads finish their execution they call their callbacks and that is how the event loop is aware of the fact that the execution of a worker thread is completed.

The main point and advantage of nodejs is that you will never need to care about those internal threads and they will stay away from your code!. All the nasty sync stuff that should normally happen in multi threaded environments will be abstracted out by nodejs framework and you can happily work on your single thread (main node thread) in a more programmer friendly environment (while benefiting from all the performance enhancements of multiple threads).

I am saying the event loop runs single threaded, not the entirety of node. I augmented my answer to point out that you don't have to deal with threads in your application code specifically. Thx for the feedback.

Node.js Event loop - Stack Overflow

node.js loops events
Rectangle 27 18

The Node.js event loop runs under a single thread. Every I/O call requires you to register a callback. Every I/O call also returns immediately, this allows you to do multiple IO operations in parallel without using threads.

I would like to start explaining with this above quote, which is one of the common misunderstandings of node js framework that I am seeing everywhere.

Node.js does not magically handle all those asynchronous calls with just one thread and still keep that thread unblocked. It internally uses google's V8 engine and a library called libuv(written in c++) that enables it to delegate some potential asynchronous work to other worker threads (kind of like a pool of threads waiting there for any work to be delegated from the master node thread). Then later when those threads finish their execution they call their callbacks and that is how the event loop is aware of the fact that the execution of a worker thread is completed.

The main point and advantage of nodejs is that you will never need to care about those internal threads and they will stay away from your code!. All the nasty sync stuff that should normally happen in multi threaded environments will be abstracted out by nodejs framework and you can happily work on your single thread (main node thread) in a more programmer friendly environment (while benefiting from all the performance enhancements of multiple threads).

I am saying the event loop runs single threaded, not the entirety of node. I augmented my answer to point out that you don't have to deal with threads in your application code specifically. Thx for the feedback.

Node.js Event loop - Stack Overflow

node.js loops events
Rectangle 27 140

I have been personally reading the source code of node.js & v8.

What I am posting here is my understanding of node.js and this might be a bit off track as well.

To understand just the javascript event loop you should consider watching these videos

To see how libeio is used with node.js in order to create async modules you should see this example.

Basically what happens inside the node.js is that v8 loop runs and handles all javascript parts as well as C++ modules [ when they are running in a main thread ( as per official documentation node.js itself is single threaded) ]. When outside of the main thread, libev and libeio handle it in the thread pool and libev provide the interaction with the main loop. So from my understanding, node.js has 1 permanent event loop: that's the v8 event loop. To handle C++ async tasks it's using a threadpool [via libeio & libev ].

eio_custom(Task,FLAG,AfterTask,Eio_REQUEST);

Which appears in all modules is usually calling the function Task in the threadpool. When it's complete, it calls the AfterTask function in the main thread. Whereas Eio_REQUEST is the request handler which can be a structure / object whose motive is to provide communication between the threadpool and main thead.

@Raynos libuv aims to make sure its x-platfousing multiple libraries . Right ? hence using libuv is a good idea

Of course libuv is a good idea

@Abhishek From Doc process.nextTick - On the next loop around the event loop call this callback. This is not a simple alias to setTimeout(fn, 0), it's much more efficient. Which event loop does this refer to? V8 event loop?

Is there a way to 'see' this event que? Id like to be able to see the order of calls on the stack and see new functions being pushed there to better understand what is happening... is there some variable that tells you whats been pushed to the event que?

javascript - Nodejs Event Loop - Stack Overflow

javascript node.js event-loop libev
Rectangle 27 10

While I wasn't able to find the number of waiting events in the queue I found another health metric that might be useful:

var ts=Date.now();
setImmediate(function()
{
  var delay=Date.now()-ts;
});

delay will contain the milliseconds it took from queuing the event to executing it.

This also takes cpu intensive events into account (which would not be possible by just looking at the # of events).

The measurement itself will affect the event queue as well but this should have a much lower overhead than a full profiler.

would be great if we could actually 'see' the event que... I suppose you never found a way to do this?

node.js Event Loop Diagnostics - Stack Overflow

node.js event-loop
Rectangle 27 7

Answer one, your logic is correct: second event will wait. And will execute as far as its queued callbacks time comes.

As well, remember that there is no such thing as "simultaneously" in technical world. Everything have very specific place and time.

The way node.js manages thousands of connections is that there is no need to hold thread idling while there is some database call blocking the logic, or another IO operation is processing (like streams for example). It can "serve" first request, maybe creating more callbacks, and proceed to others. Because there is no way to block the execution (except nonsense while(true) and similar), it becomes extremely efficient in spreading actual resources all over application logic.

Threads - are expensive, and server capacity of threads is directly related to available Memory. So most of classic web applications would suffer just because RAM is used on threads that are simply idling while there is database query block going on or similar. In node that's not a case.

Still, it allows to create multiple threads (as child_process) through cluster, that expands even more possibilities.

Answer Two. There is no such thing as "loop" that you might thinking about. There will be no loop behind the scenes that does checks if there is connections or any data received and so on. It is nowadays handled by Async methods as well.

So from application point of view, there is no 'main loop', and everything from developer point of view is event-driven (not event-loop).

In case with http.createServer, you bind callback as response to requests. All socket operations and IO stuff will happen behind the scenes, as well as HTTP handshaking, parsing headers, queries, parameters, and so on. Once it happens behind the scenes and job is done, it will keep data and will push callback to event loop with some data. Once event loop ill be free and will come time it will execute in node.js application context your callback with data from behind the scenes.

With database request - same story. It ill prepare and ask stuff (might do it even async again), and then will callback once database responds and data will be prepared for application context.

To be honest, all you need with node.js is to understand the concept, but not implementation of events. And the best way to do it - experiment.

what happens if createServer has callbacks (async) operations? Would first request lets say process some sync operations trigger callback and immediately? And start processing request two while the callback from the first request is still running?

Single threaded and Event Loop in Node.js - Stack Overflow

node.js event-loop
Rectangle 27 7

Answer one, your logic is correct: second event will wait. And will execute as far as its queued callbacks time comes.

As well, remember that there is no such thing as "simultaneously" in technical world. Everything have very specific place and time.

The way node.js manages thousands of connections is that there is no need to hold thread idling while there is some database call blocking the logic, or another IO operation is processing (like streams for example). It can "serve" first request, maybe creating more callbacks, and proceed to others. Because there is no way to block the execution (except nonsense while(true) and similar), it becomes extremely efficient in spreading actual resources all over application logic.

Threads - are expensive, and server capacity of threads is directly related to available Memory. So most of classic web applications would suffer just because RAM is used on threads that are simply idling while there is database query block going on or similar. In node that's not a case.

Still, it allows to create multiple threads (as child_process) through cluster, that expands even more possibilities.

Answer Two. There is no such thing as "loop" that you might thinking about. There will be no loop behind the scenes that does checks if there is connections or any data received and so on. It is nowadays handled by Async methods as well.

So from application point of view, there is no 'main loop', and everything from developer point of view is event-driven (not event-loop).

In case with http.createServer, you bind callback as response to requests. All socket operations and IO stuff will happen behind the scenes, as well as HTTP handshaking, parsing headers, queries, parameters, and so on. Once it happens behind the scenes and job is done, it will keep data and will push callback to event loop with some data. Once event loop ill be free and will come time it will execute in node.js application context your callback with data from behind the scenes.

With database request - same story. It ill prepare and ask stuff (might do it even async again), and then will callback once database responds and data will be prepared for application context.

To be honest, all you need with node.js is to understand the concept, but not implementation of events. And the best way to do it - experiment.

what happens if createServer has callbacks (async) operations? Would first request lets say process some sync operations trigger callback and immediately? And start processing request two while the callback from the first request is still running?

Single threaded and Event Loop in Node.js - Stack Overflow

node.js event-loop
Rectangle 27 62

1: If we are talking about a single-threaded application, then what processes setTimeouts while JS engine accepts more requests and executes them? Isn't that single thread will continue working on other requests? Then who is going to keep working on setTimeout while other requests keep coming and get executed.

There's only 1 thread in the node process that will actually execute your program's JavaScript. However, within node itself, there are actually several threads handling operation of the event loop mechanism, and this includes a pool of IO threads and a handful of others. The key is the number of these threads does not correspond to the number of concurrent connections being handled like they would in a thread-per-connection concurrency model.

Now about "executing setTimeouts", when you invoke setTimeout, all node does is basically update a data structure of functions to be executed at a time in the future. It basically has a bunch of queues of stuff that needs doing and every "tick" of the event loop it selects one, removes it from the queue, and runs it.

A key thing to understand is that node relies on the OS for most of the heavy lifting. So incoming network requests are actually tracked by the OS itself and when node is ready to handle one it just uses a system call to ask the OS for a network request with data ready to be processed. So much of the IO "work" node does is either "Hey OS, got a network connection with data ready to read?" or "Hey OS, any of my outstanding filesystem calls have data ready?". Based upon its internal algorithm and event loop engine design, node will select one "tick" of JavaScript to execute, run it, then repeat the process all over again. That's what is meant by the event loop. Node is basically at all times determining "what's the next little bit of JavaScript I should run?", then running it. This factors in which IO the OS has completed, and things that have been queued up in JavaScript via calls to setTimeout or process.nextTick.

2: If these setTimeout will get executed behind the scenes while more requests are coming and in and being executed, the thing carry out the async executions behind the scenes is that the one we are talking about EventLoop?

No JavaScript gets executed behind the scenes. All the JavaScript in your program runs front and center, one at a time. What happens behind the scenes is the OS handles IO and node waits for that to be ready and node manages its queue of javascript waiting to execute.

3: How can JS Engine know if it is an async function so that it can put it in the EventLoop?

There is a fixed set of functions in node core that are async because they make system calls and node knows which these are because they have to call the OS or C++. Basically all network and filesystem IO as well as child process interactions will be asynchronous and the ONLY way JavaScript can get node to run something asynchronously is by invoking one of the async functions provided by the node core library. Even if you are using an npm package that defines it's own API, in order to yield the event loop, eventually that npm package's code will call one of node core's async functions and that's when node knows the tick is complete and it can start the event loop algorithm again.

4 The Event Loop is a queue of callback functions. When an async function executes, the callback function is pushed into the queue. The JavaScript engine doesn't start processing the event loop until the code after an async function has executed.

Yes, this is true, but it's misleading. The key thing is the normal pattern is:

//Let's say this code is running in tick 1
fs.readFile("/home/barney/colors.txt", function (error, data) {
  //The code inside this callback function will absolutely NOT run in tick 1
  //It will run in some tick >= 2
});
//This code will absolutely also run in tick 1
//HOWEVER, typically there's not much else to do here,
//so at some point soon after queueing up some async IO, this tick
//will have nothing useful to do so it will just end because the IO result
//is necessary before anything useful can be done

So yes, you could totally block the event loop by just counting Fibonacci numbers synchronously all in memory all in the same tick, and yes that would totally freeze up your program. It's cooperative concurrency. Every tick of JavaScript must yield the event loop within some reasonable amount of time or the overall architecture fails.

Lets say I have a queue that will take the server 1 minute to execute, and the first thing was some async function that finished after 10 seconds. Will it go to the end of the queue or will it push itself into the line the instant it is ready?

Generally it will go to the end of the queue, but the semantics of process.nextTick vs setTimeout vs setImmediate are subtly different, although you shouldn't really have to care. I have a blog post called setTimeout and friends that goes into more detail.

Can you please elaborate? Let us say I have two callbacks and the first one has a changeColor method with execution time of 10mS and a setTimeout of 1 minute and the second has a changeBackground method with execution time of 50ms with a setTimeout of 10 seconds. I feel the changeBackground with be in the Queue first and the changeColor will be next. After that the Event loop picks the methods synchronously. Am I right?

@SheshPai it's too confusing for everyone to discuss code when written in paragraphs of English. Just post a new question with a code snippet so people can answer based on code instead of a description of code, which leaves a lot of ambiguity.

javascript - Understanding the Event Loop - Stack Overflow

javascript multithreading node.js asynchronous event-loop
Rectangle 27 62

1: If we are talking about a single-threaded application, then what processes setTimeouts while JS engine accepts more requests and executes them? Isn't that single thread will continue working on other requests? Then who is going to keep working on setTimeout while other requests keep coming and get executed.

There's only 1 thread in the node process that will actually execute your program's JavaScript. However, within node itself, there are actually several threads handling operation of the event loop mechanism, and this includes a pool of IO threads and a handful of others. The key is the number of these threads does not correspond to the number of concurrent connections being handled like they would in a thread-per-connection concurrency model.

Now about "executing setTimeouts", when you invoke setTimeout, all node does is basically update a data structure of functions to be executed at a time in the future. It basically has a bunch of queues of stuff that needs doing and every "tick" of the event loop it selects one, removes it from the queue, and runs it.

A key thing to understand is that node relies on the OS for most of the heavy lifting. So incoming network requests are actually tracked by the OS itself and when node is ready to handle one it just uses a system call to ask the OS for a network request with data ready to be processed. So much of the IO "work" node does is either "Hey OS, got a network connection with data ready to read?" or "Hey OS, any of my outstanding filesystem calls have data ready?". Based upon its internal algorithm and event loop engine design, node will select one "tick" of JavaScript to execute, run it, then repeat the process all over again. That's what is meant by the event loop. Node is basically at all times determining "what's the next little bit of JavaScript I should run?", then running it. This factors in which IO the OS has completed, and things that have been queued up in JavaScript via calls to setTimeout or process.nextTick.

2: If these setTimeout will get executed behind the scenes while more requests are coming and in and being executed, the thing carry out the async executions behind the scenes is that the one we are talking about EventLoop?

No JavaScript gets executed behind the scenes. All the JavaScript in your program runs front and center, one at a time. What happens behind the scenes is the OS handles IO and node waits for that to be ready and node manages its queue of javascript waiting to execute.

3: How can JS Engine know if it is an async function so that it can put it in the EventLoop?

There is a fixed set of functions in node core that are async because they make system calls and node knows which these are because they have to call the OS or C++. Basically all network and filesystem IO as well as child process interactions will be asynchronous and the ONLY way JavaScript can get node to run something asynchronously is by invoking one of the async functions provided by the node core library. Even if you are using an npm package that defines it's own API, in order to yield the event loop, eventually that npm package's code will call one of node core's async functions and that's when node knows the tick is complete and it can start the event loop algorithm again.

4 The Event Loop is a queue of callback functions. When an async function executes, the callback function is pushed into the queue. The JavaScript engine doesn't start processing the event loop until the code after an async function has executed.

Yes, this is true, but it's misleading. The key thing is the normal pattern is:

//Let's say this code is running in tick 1
fs.readFile("/home/barney/colors.txt", function (error, data) {
  //The code inside this callback function will absolutely NOT run in tick 1
  //It will run in some tick >= 2
});
//This code will absolutely also run in tick 1
//HOWEVER, typically there's not much else to do here,
//so at some point soon after queueing up some async IO, this tick
//will have nothing useful to do so it will just end because the IO result
//is necessary before anything useful can be done

So yes, you could totally block the event loop by just counting Fibonacci numbers synchronously all in memory all in the same tick, and yes that would totally freeze up your program. It's cooperative concurrency. Every tick of JavaScript must yield the event loop within some reasonable amount of time or the overall architecture fails.

Lets say I have a queue that will take the server 1 minute to execute, and the first thing was some async function that finished after 10 seconds. Will it go to the end of the queue or will it push itself into the line the instant it is ready?

Generally it will go to the end of the queue, but the semantics of process.nextTick vs setTimeout vs setImmediate are subtly different, although you shouldn't really have to care. I have a blog post called setTimeout and friends that goes into more detail.

Can you please elaborate? Let us say I have two callbacks and the first one has a changeColor method with execution time of 10mS and a setTimeout of 1 minute and the second has a changeBackground method with execution time of 50ms with a setTimeout of 10 seconds. I feel the changeBackground with be in the Queue first and the changeColor will be next. After that the Event loop picks the methods synchronously. Am I right?

@SheshPai it's too confusing for everyone to discuss code when written in paragraphs of English. Just post a new question with a code snippet so people can answer based on code instead of a description of code, which leaves a lot of ambiguity.

javascript - Understanding the Event Loop - Stack Overflow

javascript multithreading node.js asynchronous event-loop
Rectangle 27 103

What are the practical consequences of this?

One go-around of the event loop will have exactly one task being processed from the macrotask queue (this queue is simply called the task queue in the WHATWG specification). After this macrotask has finished, all available microtasks will be processed, namely within the same go-around cycle. While these microtasks are processed, they can queue even more microtasks, which will all be run one by one, until the microtask queue is exhausted.

If a microtask recursively queues other microtasks, it might take a long time until the next macrotask is processed. This means, you could end up with a blocked UI, or some finished I/O idling in your application.

However, at least concerning Node.js's process.nextTick function (which queues microtasks), there is an inbuilt protection against such blocking by means of process.maxTickDepth. This value is set to a default of 1000, cutting down further processing of microtasks after this limit is reached which allows the next macrotask to be processed)

Basically, use microtasks when you need to do stuff asynchronously in a synchronous way (i.e. when you would say perform this (micro-)task in the most immediate future). Otherwise, stick to macrotasks.

Although there's a microtask checkpoint in the event loop, this isn't where most developers will encounter microtasks. Microtasks are processed when the JS stack empties. This can happen many times within a task, or even within the render steps of the event loop.

javascript - Difference between microtask and macrotask within an even...

javascript node.js promise event-loop
Rectangle 27 31

There is a fantastic video tutorial by Philip Roberts, which explains javascript event loop in the most simplistic and conceptual way. Every javascript developer should have a look.

Here is the video link on Youtube.

I watched it and it was indeed the best explanation ever.

A must watch video for JavaScript fans and enthusiasts.

came wandering here.. and this is one of the best explanation i got.. thank you for sharing...:D

javascript - Understanding the Event Loop - Stack Overflow

javascript multithreading node.js asynchronous event-loop
Rectangle 27 17

Both nginx and Node use an asynchronous and event-driven approach. The communication between them will go more or less like this:

  • nginx receives a request
  • Node receives the request from nginx
  • Node handles the request with minimal CPU usage, until at some point it needs to issue one or more I/O requests (read from a database, write the response, etc). At this point it launches all these I/O requests and goes back to wait for more requests.
  • The above can repeat lots of times. You could have hundreds of thousands of requests all in a non-blocking wait state where nginx is waiting for Node and Node is waiting for I/O. And while this happens both nginx and Node are ready to accept even more requests!
  • Eventually async I/O started by the Node process will complete and a callback function will get invoked.
  • If there are still I/O requests that haven't completed for this request, then Node goes back to its loop one more time. It can also happen that once an I/O operation completes this data is consumed by the Node callback and then new I/O needs to happen, so Node can start more async I/O requests before going back to the loop.
  • Eventually all I/O operations started by Node for a particular request will be complete, including those that write the response back to nginx. So Node ends this request, and then as always goes back to its loop.
  • nginx receives an event indicating that response data has arrived for a request, so it takes that data and writes it back to the client, once again in a non-blocking fashion. When the response has been written to the client and event will trigger and nginx will then end the request.

You are asking about what would happen if nginx and Node can handle a different number of maximum connections. They really don't have a maximum, the maximum in general comes from operating system configuration, for example from the maximum number of open handles the system can have at a time or the CPU throughput. So your question does not really apply. If the system is configured correctly and all processes are I/O bound, neither nginx or Node will ever block.

Putting Apache in front of Node will only work well if you can guarantee that your Apache never blocks (i.e it never reaches its maximum connection limit). This is hard/impossible to achieve for large number of connections, because Apache uses an individual process or thread for each connection. nginx and Node scale really well, Apache does not.

Running Node without another server in front works fine and it should be okay for small/medium load sites. The reason putting a web server in front of it is preferred is that web servers like nginx come with features that Node does not have and you would need to implement yourself. Things like caching, load balancing, running multiple apps from the same server, etc.

The Node.js event loop - nginx/apache - Stack Overflow

apache node.js nginx
Rectangle 27 31

There is a fantastic video tutorial by Philip Roberts, which explains javascript event loop in the most simplistic and conceptual way. Every javascript developer should have a look.

Here is the video link on Youtube.

I watched it and it was indeed the best explanation ever.

A must watch video for JavaScript fans and enthusiasts.

came wandering here.. and this is one of the best explanation i got.. thank you for sharing...:D

javascript - Understanding the Event Loop - Stack Overflow

javascript multithreading node.js asynchronous event-loop
Rectangle 27 32

You can call process._getActiveRequests() to get a list of active I/O requests and process._getActiveHandles() to get a list of open handles/file descriptors.

Node.js: inspect what's left in the event loop that's preventing the s...

node.js
Rectangle 27 32

You can call process._getActiveRequests() to get a list of active I/O requests and process._getActiveHandles() to get a list of open handles/file descriptors.

Node.js: inspect what's left in the event loop that's preventing the s...

node.js
Rectangle 27 33

Update: I also gave a talk about this https://www.youtube.com/watch?v=cCOL7MC4Pl0. The talk goes into more detail, including how tasks & microtasks interact with rendering.

javascript - Difference between microtask and macrotask within an even...

javascript node.js promise event-loop
Rectangle 27 17

Both nginx and Node use an asynchronous and event-driven approach. The communication between them will go more or less like this:

  • nginx receives a request
  • Node receives the request from nginx
  • Node handles the request with minimal CPU usage, until at some point it needs to issue one or more I/O requests (read from a database, write the response, etc). At this point it launches all these I/O requests and goes back to wait for more requests.
  • The above can repeat lots of times. You could have hundreds of thousands of requests all in a non-blocking wait state where nginx is waiting for Node and Node is waiting for I/O. And while this happens both nginx and Node are ready to accept even more requests!
  • Eventually async I/O started by the Node process will complete and a callback function will get invoked.
  • If there are still I/O requests that haven't completed for this request, then Node goes back to its loop one more time. It can also happen that once an I/O operation completes this data is consumed by the Node callback and then new I/O needs to happen, so Node can start more async I/O requests before going back to the loop.
  • Eventually all I/O operations started by Node for a particular request will be complete, including those that write the response back to nginx. So Node ends this request, and then as always goes back to its loop.
  • nginx receives an event indicating that response data has arrived for a request, so it takes that data and writes it back to the client, once again in a non-blocking fashion. When the response has been written to the client and event will trigger and nginx will then end the request.

You are asking about what would happen if nginx and Node can handle a different number of maximum connections. They really don't have a maximum, the maximum in general comes from operating system configuration, for example from the maximum number of open handles the system can have at a time or the CPU throughput. So your question does not really apply. If the system is configured correctly and all processes are I/O bound, neither nginx or Node will ever block.

Putting Apache in front of Node will only work well if you can guarantee that your Apache never blocks (i.e it never reaches its maximum connection limit). This is hard/impossible to achieve for large number of connections, because Apache uses an individual process or thread for each connection. nginx and Node scale really well, Apache does not.

Running Node without another server in front works fine and it should be okay for small/medium load sites. The reason putting a web server in front of it is preferred is that web servers like nginx come with features that Node does not have and you would need to implement yourself. Things like caching, load balancing, running multiple apps from the same server, etc.

The Node.js event loop - nginx/apache - Stack Overflow

apache node.js nginx
Rectangle 27 12

The node.js project began in 2009 as a JavaScript environment decoupled from the browser. Using Googles V8 and Marc Lehmanns libev, node.js combined a model of I/O evented with a language that was well suited to the style of programming; due to the way it had been shaped by browsers. As node.js grew in popularity, it was important to make it work on Windows, but libev ran only on Unix. The Windows equivalent of kernel event notification mechanisms like kqueue or (e)poll is IOCP. libuv was an abstraction around libev or IOCP depending on the platform, providing users an API based on libev. In the node-v0.9.0 version of libuv libev was removed.

Also one picture which describe the Event Loop in Node.js by @BusyRich

The following diagram shows a simplified overview of the event loop's order of operations.

>        timers         
  
  
       I/O callbacks     
  
  
       idle, prepare     
        
           incoming:   
           poll          <  connections, 
           data, etc.  
        
          check          
  
  
    close callbacks

note: each box will be referred to as a "phase" of the event loop.

  • timers: this phase executes callbacks scheduled by setTimeout() and setInterval().
  • I/O callbacks: executes almost all callbacks with the exception of
  • close callbacks, the ones scheduled by timers, and setImmediate(). idle, prepare: only used internally.
setImmediate()
socket.on('close', ...)

Between each run of the event loop, Node.js checks if it is waiting for any asynchronous I/O or timers and shuts down cleanly if there are not any.

In the node-v0.9.0 version of libuv libev was removed
changelog

@intekhab, Per this link, I think the libuv based on libeio could be used as event loop in node.js.

javascript - Nodejs Event Loop - Stack Overflow

javascript node.js event-loop libev
Rectangle 27 9

It's fairly simple really. Internally, node.js consists of this type of loop:

  • Get something from the event queue
  • When the above task is done, get the next item from the event queue
  • Run whatever task is indicated and run it until it returns

If at some point, there is nothing in the event queue, then go to sleep until something is placed in the event queue.

So, if a piece of Javascript is sitting in a while() loop, then that task is not finishing and per the above sequence, nothing new will be picked out of the event queue until that prior task is completely done. So, a very long or forever running while() loop just gums up the works. Because Javascript only runs one task at a time (single threaded for JS execution), if that one task is spinning in a while loop, then nothing else can ever execute.

Here's a simple example that might help explain it:

var done = false;

 // set a timer for 1 second from now to set done to true
 setTimeout(function() {
      done = true;
 }, 1000);

 // spin wait for the done value to change
 while (!done) { /* do nothing */}

 console.log("finally, the done value changed!");

Some might logically think that the while loop will spin until the timer fires and then the timer will change the value of done to true and then the while loop will finish and the console.log() at the end will execute. That is NOT what will happen. This will actually be an infinite loop and the console.log() statement will never be executed.

The issue is that once you go into the spin wait in the while() loop, NO other Javascript can execute. So, the timer that wants to change the value of the done variable cannot execute. Thus, the while loop condition can never change and thus it is an infinite loop.

Here's what happens internally inside the JS engine:

done
false
setTimeout()
  • 1 second into the while loop spinning, the timer fires internally to the JS engine and the timer callback is added to the event queue. This likely occurs on a different thread, internal to the JS engine.
  • The while loop keeps spinning because the done variable never changes. Because it continues to spin, the JS engine never finishes this thread of execution and never gets to pull the next item from the event queue.

thanks @jfriend00. Thats a great answer and just what I was looking for. I hope others will upvote it too, not that you need the rep ;)

So I get a very long run around the bush that while loops block in js.

@marshalcraft - ANY loop in Javascript blocks. Javascript is single threaded and event driven so as long as a loop is running, nothing else except the code in the loop can run. And, it's not just loops. Any long running function keeps other things from running. Single threaded - Javascript can only do one synchronous thing at a time. All loops are synchronous. In case you missed it, the summary is in my third paragraph after it explains how the event queue works (which is the key to understanding all this). I don't think that's a very long run around the bush.

I apologize jftiend. I was over critical. So non asynchronous functions block. But really a while loop in a asynchronous function would still block. Seems a while loop from start to exit is a single unit of asynchronous execution. I understand js is single threaded. But it doesn't necessarily execute code inline, so it pauses in some cases to continue asynchronous code, or events. Being as it doesn't use time to dictate how much to execute, it must use "atomic" or basic units of execution. Like run global scope code for a little, pause to handle event or do some work on asynchronous function.

It is conceivable that the js interpreter or runtime could do this on one thread. Also forgive my probably poor js verbage and terminology. I'm not strong with js.

node.js - Why does a while loop block the node event loop? - Stack Ove...

node.js