Node.js - what exactly happens upon a new client request - node.js

I want to understand more exactly what happens when a server receives a client request on a Node.js server. With a more traditional server, a new thread is created to handle the new client session.
But in Node.js and other event-loop style servers, what exactly happens? What part of the codebase first gets executed? With node, I am almost certain something in the http module handles the new request first.
I want to know a little more about the details of how this works in a sort of compare and contrast style between the two types of handling of client connections.

In a nutshell:
Node uses libuv to manage incoming connections and data events
Events are placed in a queue to be handled on the next tick of the event loop
When bytes start arriving, they are fed in to the native-code http parser
The parser calls a callback in JS-land with the header contents
The rest of the JS HTTP code dispatches the request to user code, which may be Express

Related

How does NodeJS process incoming requests

I have been studying and doing hands-on practice with NodeJS since few weeks now.
I understand that it is a single-threaded, event based, javascript runtime environment.
It uses an event loop to process javascript statements and any incoming IO requests from clients.
But I am getting a hard time understanding that when a request comes to NodeJS from an external client like ReactJS or Postman. How it reaches the event loop and in which phase of event loop does it get processed. So far I have read many articles which go on repeating the same thing about various phases but I am not convinced whether my understanding of how request is handled by NodeJS is correct.
So here is my understanding:
NodeJS listens on a port for any incoming requests
When a client sends the request to that port, then the request is picked up by NodeJS
Now it goes to Event Queue and waits there until it gets picked up in the Poll phase by the event loop
Also there are a couple of doubts I have around my understanding:
I know that we setup various routes in our node app that trigger certain logic when a request comes in. But at what point/phase does NodeJS do this route matching of incoming requests.
What happens after event loop picks up a request from Event Queue? How does it get processed by the V8 engine?

Transactions / request-response-pattern in flow based/reactive programming

So I have been reading about flow based programming (FBP) in the last few days and I have also been reading J. Paul Morrison's book about it. However I feel I still can't really wrap my head around it. The general concept is that you see programming as some sort of assembly line where you have components that take some packet as input and produce some packets as output. You can connect these components and packets travel through the network. While I totally see how this can work for ETL type applications or batch processing, I have no good idea how you could handle things like synchronous request/response patterns or database transactions with it.
For example let's say I have a web server implemented as FPB. This webserver has a GET /user/{id} which should return a JSON with some information about a user. It also has a POST /user/{id} where you can update the user by sending some JSON back to the server. So here is how I would imagine this flow to be looking:
I tried to have many re-usable components instead of putting the whole logic of handling a request into a single component. So there is a HTTP server component which sends out requests to a dispatcher component which then dispatches the requests into subsequent flows. In each flow the request is parsed by a generic "Request parser" component which outputs various parts of the request into the rest of the flow.
The upper part is quite straightforward, I read the entity of the user with the given ID from DB, serialize the object to JSON and then send it back. However at this point we don't really have a reference to the HTTP request anymore, so how would I know where to send this request to?
On the lower part we have some additional complexity because I would like to write to the database in a transactional way. So first a transaction is started (in parallel the request body is parsed into some object), then the user object is retrieved from the database and merged with the inputs from the request. At the end it is written back to the database and the transaction is committed. Finally some "OK" status is responded to the caller. Here I have the additional problem that when committing the transaction I really don't know which transaction to commit. And of course when sending the response I don't know which request to send it to.
So both problems seem to have something in common - a kind of "Context" that spans over many components. On one example it is a HTTP request/response context in the other a transactional context. In regular programming, these contexts are usually handled at the thread level. Since a request runs in a single thread, the transaction and request contexts are bound to a thread-local so they can be accessed everywhere as long as everything is running in the same thread.
In flow based programming, every component runs independently and ideally on separate threads. This is actually a key thing because it allows for parallelization and effective use of multiple processors. However when that thread-local context is no longer there, how can you handle these problems in flow based programming? This would get even more complicated with proper error handling (which I left out in my example).
I figure that when you do reactive style programming where most of the processing is asynchronous and multithreaded as well you will have the same issues, so I wonder if there are patterns to handle this. Do you have real life experience with either reactive style programming or flow based programming and have some hints on how I could solve this problem?
I wrote a quick answer on Twitter - thought I would post it here as well... Apologies for double-posting!
I like substreams for this/these problem(s), where the first Information Packet in the substream provides the "context" you were talking about. This may help: https://github.com/jpaulm/javafbp-websockets... HTH!
PS This loop-style network topology is also the basis of Facebook's new "Flux" technology - see Jing Chen's presentation, in which she compares this approach with MVC: https://www.youtube.com/watch?v=nYkdrAPrdcw
Hopefully this may nudge you in the right direction. I had a similar issue where I needed to perform a synchronous operation in an asynchronous microservice architecture.
How I solved it was using the Observer pattern. I have 3 components; a http server, a callback server and a timer wheel. The http server similar to yours receives the incoming request, the callback server receives the overal result after asynchronous processing and the timer wheel that queues the original http context and reconciles the response to the http request.
When an incoming request is received, the http server creates a correlation id ,appends it to the request metadata, appends the callback server url to the request metadata and finally adds the request and the original http context together into the timer wheel. Then the http server would pass the request to the dispatcher like in your case and send messages to the relevant components for asynchronous processing.
Depending on the outcome of execution of the current processing component, it will retrieve the callback url from the metadata and send the response to the callback server.In your case there's the json serialization or the database write that would do this. The callback server will then extract the correlation Id that was appended and get the corresponding http context and write the response.
NB each timer object in the timer wheel has a timeout that's configurable, that way if the asynchronous processing delays it will timeout and return a configurable message to the http client of the corresponding http context.

Why can't I use res.json() twice in one post request?

I've got an chatbot app where I want to send one message e.g. res.json("Hello") from express, then another message later e.g. res.json("How are you doing"), but want to process some code between the two.
My code seems to have some problems with this, because when I delete the first res.json() then the second one works fine and doesn't cause any problems.
Looking in my heroku logs, I get lots of gobbledy gook response from the server, with an IncomingMessage = {}, containing readableState and Server objects when I include both of these res.json() functions.
Any help would be much appreciated.
HTTP is request/response. Client sends a request, server sends ONE response. Your first res.json() is your ONE response. You can't send another response to that same request. If it's just a matter of collecting all the data before sending the one response, you can rethink your code to collect all the data before sending the one response.
But, what you appear to be looking for is "server push" where the server can send data to the client continually whenever it wants to. The usual solution for that is a webSocket connection (or socket.io which is built on top of webSocket and adds more features).
In the webSocket/socket.io architecture, the client makes a connection the server and the connection is kept open indefinitely. Then either side of the connection can send messages to the other end. This is most useful when the server wants to "push" data to the client at any time. In this case, the client establishes the connection, then the server can send data to the client over that connection at any time. The client registers a listener for incoming messages and will be notified anytime the server sends it some data.
Both webSocket and socket.io are fully supported in modern browsers and in node.js. I would personally recommend using socket.io because some of the features it adds (a messaging layer, auto-reconnect, etc...) are very useful.
To use a continuously connected socket like this, you will have to make sure your hosting infrastructure is properly configured to allow it.
res.json() always sends the response to the client immediately (calling it again will cause an error). If you need to gradually build up a response then you can progressively decorate a plain old javascript object; for example, appending items to an array. When you are done call res.json() with the constructed response.
But you should post your code so we can see what's happening.

What is the best way doing intervals without blocking the event loop in Node Js server?

im really new to node.js and i have a beginners question.
I plan to creat a node server that will execute a http request for a json file every 1-2 seconds.
The reason for doing a request so fast is because the json file im requesting is changing constantly.
What is the correct way doing that and not blocking the event loop?
Is it safe to put the request code in a function and call it in a setTimeout() function?
Should i run the requests in a child process?
The whole point of asynchronicity is that it is asynchronous. When you issue the HTTP request, it is sent off more or less instantly and node returns to other business, waking up only when the response is received. The only thing that could cause a "blocking" of the event loop in your case is very intensive processing either preparing the request or processing the response.
That is why on the front page of the node website it says "node uses an event-driven, non-blocking I/O model".

Catching HTTP response event

I am building a Node web application (using Express) and to keep everything as DRY as possible, I automatically acquire database connection for each request but I also need to release it (back to the pool).
I could do that manually in every route but that would be just polluting the code. I figured that I should listen to server events and release it once response is either finished generating or sending. What options do I have? What events (and inside which object (app, request or whatever) are triggered when response is complete?
res is inherited from EventEmitter, and can use default events as well as you can emit own ones.
So one of the most common would be finish (in node.0.8.12 and older end) event:
res.on('finish', function() {
// request processing finished
});
You can attach that event for all requests if you want, or to specific early in their roots.
Additionally you can create middleware, that would get DB connection, and attach finish event and possibly timeouts. And then all you will need is to add that middleware into routes, so minimum of repetitive coding.
In mean time, I would recommend you not to create DB connection for each request, as it is a big overhead and unnecessary use of sockets as well as IO handlers. You can freely use onse single connection, and it will be as efficient from performance point of view.

Resources