Decoding Backend Architecture: Unraveling the Mechanisms Behind Backend Operations - part 1


We all know that the backend is the key to running a website. Most of the time, the website user doesn’t recognize that something is under the hood taking all the load of the application, he is just giving instructions via whatever the UI exposed. But as a web developer, we all know that all the loads are taken by the service that’s running under the hood called backend.

Let’s learn the underlying architecture of a backend server. It won’t be the exact direction of operating your server, but the fundamental technique is mostly the same.

The broad picture of a request

There are multiple ways of communicating with the backend server. The most common way is to use an HTTP request. An HTTP request could contain path, queries, headers, and body. There are 7 types of HTTP methods available GET, HEAD, POST, PUT, PATCH, DELETE, and OPTIONS. The OPTIONS method is used by the browser to determine what requests this server accepts more later. There are several rules for sending requests by different types of methods. The GET and HEAD methods are used for getting information from the server, they can’t contain any body in the request, all the other methods can send a body. Also, it’s the sender’s responsibility to provide necessary information about the request body type via the 'Content-Type': '...' header property. We can send text-based data with various formats most common being application/json and application/x-www-form-urlencoded. But for sending binary files we have to use the multipart/formdata type.

The broad picture of a server

Now we have a better understanding of a Request. It’s time to understand how this request gets handled by a server. The server receives a raw request, that contains the path + queries, headers, and body as string or binary bytes. Let’s learn about the steps that a server goes through for requests then we’ll learn more about it.

  • Parse request data
  • Find a route for the path
  • Call the handler with the parsed data
  • Fall into 404 if there are no handlers for the path
  • Return the provided response from the handler

Parse request data

Most of the time we don’t have to worry about this part, almost all the framework/library does this for us (don’t have to reinvent :D). Let’s take an overall look at this process, the server got a raw request, parsed the URL with headers, determined the request body type from the Content-Type: ... property, and then provided it to the appropriate driver for converting this data into the language-specific data type, like object/array.

Find a route for the path

Now this is an interesting part. It’s the programmer’s design choice how they want to handle the request. Here, we have a request with a specific path + queries, headers, and body it’s our time to shine :D. Most of the time we have already registered some route with its path and attached a handler for the specific path. Then we run a matching algorithm to find the specified handler for this path.

Fall into 404 if there are no handlers for the path

Matching path could fail most of the time :D, you don’t know what a user could type in the browser or maybe use an HTTP client like PostMan. So, we have to have a backup plan for telling the user that it’s their fault :D. When couldn’t find any specified handler for the path we simply responded with a 404 status (more later).

Return the provided response from the handler

When there are any matching handler found we call the handler with the requested data and the handler method decide what to do with this request and what response should be returned for this request.

That’s it :D

We now have a better understanding of a server and how it works, but it’s just an overview, we’ll build a web server from scratch and understand the fundamentals from there using node.js. Let’s do our first coding with a hello world server in node.js.

const http = require('http');

const server = http.createServer((req, res) => {
  // Check the request path
  if (req.url === '/hello-world') {
    // Set the response headers for successful response
    res.writeHead(200, {'Content-Type': 'text/plain'});
    // Send the "Hello, World!" response
    res.end('Hello, World!\n');
  } else {
    // Set the response headers for 404 Not Found
    res.writeHead(404, {'Content-Type': 'text/plain'});
    // Send the "404 Not Found" response
    res.end('404 Not Found\n');
  }
});

// Set the server to listen on port 3000
const port = 3000;
server.listen(port, () => {
  console.log(`Server running at http://localhost:${port}/`);
});

That concludes our current session. We’ll continue learning in segments. Thank you for reading with patience! 😊


Series Breakdown: