# HTTP Fundamentals

Course: [Express.js](https://www.devtutorials.ai/learn/expressjs) · Section: Express.js Foundations
Source: https://www.devtutorials.ai/learn/expressjs/foundations/http-fundamentals

> Clients and servers, requests and responses, URLs, origins, paths and endpoints, headers and bodies, HTTP methods, status codes, content types, and the Express request-response cycle.

## HTTP Introduction

**HTTP** = the set of rules that browsers, apps and servers use to talk on the web.

- HTTP stands for HyperText Transfer Protocol.
- One side asks a question. This is the **request**.
- The other side answers. This is the **response**.
- Every Express route you write answers one kind of request.
- Knowing HTTP makes every later Express lesson easier.

**Simple lesson:** HTTP is a simple ask-and-answer conversation.

### A Real-World Example

Think about ordering at the school canteen counter.

1. You walk up and say "One masala dosa, please".
2. The counter staff checks the menu.
3. They hand you a plate, or say "Sorry, finished".
4. Every order is a new, separate conversation.

Your order is the request. The plate or the "sorry" is the response.

In this lesson, you will learn:

1. What clients, servers, requests and responses are.
2. The parts of a URL and an endpoint.
3. What headers and bodies carry.
4. The main HTTP methods and status codes.
5. Content types and the Express request-response cycle.

## Clients and Servers

- **Client** = the program that sends the request. Examples: a browser, a phone app, curl.
- **Server** = the program that waits and answers. Your Express app is a server.
- A client always speaks first. A server never calls a client by itself.
- One server can answer thousands of clients.
- The same computer can run both, like your browser and `localhost:3000`.

<figure className="xfig ngc-fig">
<svg viewBox="0 0 560 230" role="img" aria-labelledby="xfig-msg" style={{ width: "100%", maxWidth: 560, height: "auto" }}>
  <title id="xfig-msg">A request message and a response message, each with a first line, headers and a body</title>
  <g style={{ fontFamily: "var(--mono)", fontSize: 12 }}>
    <rect x="10" y="10" width="260" height="210" rx="10" style={{ fill: "var(--ngc-blue-soft)", stroke: "var(--ngc-blue)", strokeWidth: 2 }} />
    <text x="24" y="34" style={{ fill: "var(--ngc-blue)", fontFamily: "var(--sans)", fontWeight: 700, fontSize: 13 }}>Request</text>
    <text x="24" y="62" style={{ fill: "var(--ngc-orange)", fontWeight: 700 }}>POST /orders HTTP/1.1</text>
    <text x="24" y="90" style={{ fill: "var(--ink)" }}>Host: localhost:3000</text>
    <text x="24" y="108" style={{ fill: "var(--ink)" }}>Content-Type: application/json</text>
    <text x="24" y="126" style={{ fill: "var(--ink)" }}>Accept: application/json</text>
    <text x="24" y="166" style={{ fill: "var(--ngc-green)" }}>{"{ \"item\": \"Idli\", \"qty\": 2 }"}</text>
    <rect x="290" y="10" width="260" height="210" rx="10" style={{ fill: "var(--ngc-green-soft)", stroke: "var(--ngc-green)", strokeWidth: 2 }} />
    <text x="304" y="34" style={{ fill: "var(--ngc-green)", fontFamily: "var(--sans)", fontWeight: 700, fontSize: 13 }}>Response</text>
    <text x="304" y="62" style={{ fill: "var(--ngc-orange)", fontWeight: 700 }}>HTTP/1.1 201 Created</text>
    <text x="304" y="90" style={{ fill: "var(--ink)" }}>Content-Type: application/json</text>
    <text x="304" y="108" style={{ fill: "var(--ink)" }}>Content-Length: 31</text>
    <text x="304" y="126" style={{ fill: "var(--ink)" }}>X-Powered-By: Express</text>
    <text x="304" y="166" style={{ fill: "var(--ngc-green)" }}>{"{ \"id\": 7, \"item\": \"Idli\" }"}</text>
  </g>
  <g style={{ fontFamily: "var(--sans)", fontSize: 11, fill: "var(--muted)" }}>
    <text x="140" y="210" textAnchor="middle">first line, headers, blank line, body</text>
    <text x="420" y="210" textAnchor="middle">status line, headers, blank line, body</text>
  </g>
</svg>
<figcaption>Both messages have the same shape: a first line, headers, then a body.</figcaption>
</figure>

**Simple lesson:** The client asks first. The server answers.

## URLs, Origins, Paths and Endpoints

Take this URL: `http://localhost:3000/menu?veg=true`

- **Protocol** = `http`. The rules to use. Real sites use `https`, the safe version.
- **Host** = `localhost`. The computer to talk to.
- **Port** = `3000`. The door on that computer.
- **Origin** = protocol + host + port: `http://localhost:3000`.
- **Path** = `/menu`. Which thing you want.
- **Query string** = `?veg=true`. Extra options, as name=value pairs.
- **Endpoint** = a method plus a path that your server answers, such as `GET /menu`.

Run this lab. The server sends back the parts of each request it gets.

- Press each quick request and compare the answers.
- The path stays `/menu`. Only the query changes.
- Only the POST request has a body and a content type.

Real sites use `https`, which encrypts the whole message. Local development uses plain `http` on `localhost`, which is fine on your own computer.

**Simple lesson:** The path says what you want. The query says how you want it.

## Headers and Bodies

**Headers** = short name-value notes about the message.

- `Content-Type` says what kind of data the body holds.
- `Accept` says what kind of answer the client wants.
- `User-Agent` names the client program.
- `Authorization` carries a login token.
- Request headers travel to the server. Response headers travel back.

**Body** = the main data of the message.

- A request body carries data you send, such as a new order.
- A response body carries the answer, such as the menu.
- `GET` requests usually have no body.

Press **Headers** in the response panel of any lab to see real response headers.

**Simple lesson:** Headers describe the message. The body is the message.

## HTTP Methods

**Method** = the verb of a request. It says what you want to do.

- **GET:** read something. Example: get the menu.
- **POST:** create something new. Example: place an order.
- **PUT:** replace something fully. Example: replace order 7.
- **PATCH:** change part of something. Example: change only the quantity.
- **DELETE:** remove something. Example: cancel an order.
- **OPTIONS:** ask which methods a path allows.
- **HEAD:** like GET, but only the headers come back.

- Each method on the same path runs a different handler.
- OPTIONS comes back with an `Allow` header. Express builds it for you.
- HEAD comes back with headers and an empty body. Express uses your GET handler.

### Safe and Idempotent

- **Safe** = the method only reads. GET, HEAD and OPTIONS are safe.
- **Idempotent** = sending it twice has the same effect as once. GET, PUT and DELETE are idempotent.
- POST is neither. Two POSTs may create two orders.

**Simple lesson:** The method is the verb. The path is the thing.

## HTTP Status Codes

**Status code** = a three-digit number at the start of every response.

- **1xx Informational:** "wait, more is coming". Rare in Express apps.
- **2xx Success:** 200 OK, 201 Created, 204 No Content.
- **3xx Redirection:** 301 Moved Permanently, 302 Found, 304 Not Modified.
- **4xx Client error:** 400 Bad Request, 401 Unauthorized, 403 Forbidden, 404 Not Found.
- **5xx Server error:** 500 Internal Server Error, 503 Service Unavailable.

### Choosing the Right Code

- Did it work and return data? Use **200**.
- Did it create something? Use **201**.
- Did the client send bad data? Use **400**.
- Is the client not logged in? Use **401**. Logged in but not allowed? Use **403**.
- Does the thing not exist? Use **404**.
- Did your own code fail? Express sends **500**.

Easy way to remember: **4xx means "you" made a mistake. 5xx means "we" made a mistake.**

**Simple lesson:** The status code is the short answer. The body is the long answer.

## Content Types

The `Content-Type` header tells the other side how to read the body.

- **application/json:** data for programs, such as `{"item":"Idli"}`.
- **text/plain:** plain text with no formatting.
- **text/html:** a web page.
- **application/x-www-form-urlencoded:** data from a normal HTML form.
- **multipart/form-data:** forms that upload files.
- **application/octet-stream:** raw bytes, such as a downloaded file.

- Open **Headers** for each answer and read `Content-Type`.
- `/html` and `/text` send the same characters. Only the type differs.
- The browser shows a heading for one, and raw tags for the other.

**Simple lesson:** Same bytes, different `Content-Type`, different meaning.

## The Express Request-Response Cycle

**Request-response cycle** = the full trip from one request to its one response.

1. **Client request:** a request arrives at your server.
2. **Middleware:** functions you added with `app.use` run in order.
3. **Route matching:** Express finds a route with the same method and path.
4. **Route handler:** your function runs.
5. **Server response:** the handler sends one answer.
6. **End:** the cycle ends. Nothing more can be sent.

- `/menu` prints two lines, then answers.
- `/forgot` prints two lines, then the client gets **No response**.
- A real browser would show a spinning wheel until it gives up.

Every request must end with exactly one response. Zero responses leave the client waiting. Two responses cause an error.

**Simple lesson:** One request in, one response out. Always.

## Common mistakes

<div className="tscroll">

| Mistake | Wrong idea | Correct idea | What goes wrong |
|---|---|---|---|
| Using GET to create orders | Any method works for anything | POST creates, GET only reads | Browsers and caches may repeat the request |
| Sending 200 with an error message | The body explains the error | The status code must match | Clients think it worked |
| Using 401 for "not allowed" | 401 and 403 are the same | 401 = not logged in, 403 = not allowed | Confusing login screens |
| Forgetting to send a response | Returning from the handler is enough | Call `res.send`, `res.json` or similar | The request hangs |
| Matching `req.url` with a query | The URL is just the path | The path and query are separate | Routes stop matching |
| Wrong `Content-Type` | The client guesses the format | The header decides the format | JSON shows as text, HTML shows as code |

</div>

## Check Yourself

## Exercises

## What to Remember

- HTTP is a request and a response, every time.
- A URL has an origin, a path and an optional query string.
- Headers describe the message. The body carries the data.
- Methods are verbs: GET reads, POST creates, PUT replaces, PATCH changes, DELETE removes.
- Status codes: 2xx worked, 3xx go elsewhere, 4xx client mistake, 5xx server mistake.
- Every request needs exactly one response.

Next: **Application, Request and Response**. You will learn the `app` object, its settings and how to mount one app inside another.
