Serverul te apelează pe tine
Un server web Node.js este construit din handlere: funcții cu forma (req: IncomingMessage, res: ServerResponse) => void, din modulul încorporat node:http. Serverul acceptă conexiunile și îți apelează handlerul o dată pentru fiecare cerere — req conține tot ce ține de cerere, iar tot ce scrii în res devine răspunsul.
Un server real pornește cu server.listen(8080) și rulează la nesfârșit. Exemplele de aici apelează în schimb server.listen(0): portul 0 înseamnă „orice port liber”, așa că nimic nu se poate ciocni. Apoi fiecare exemplu citește portul real, își face propria cerere cu fetch și apelează server.close() — astfel fiecare program rulează și se termină singur.
Un prim handler
Cel mai mic handler posibil scrie o linie de text. Tot ce face un API — JSON, coduri de status, rutare — se întâmplă în interiorul aceleiași forme de funcție.
Salut de la un handler
Handlerul scrie în res; clientul citește exact asta drept corp al răspunsului, iar statusul 200 OK este completat automat.
Ieșire: program TypeScript și rezultatul capturat
import { createServer, type IncomingMessage, type ServerResponse } from "node:http"
// Cel mai mic handler: o cerere intră, o linie de text iese.
function hello(req: IncomingMessage, res: ServerResponse): void {
res.end("salut de la server\n")
}
async function main(): Promise<void> {
const server = createServer(hello)
await new Promise<void>(resolve => server.listen(0, () => resolve()))
const port = (server.address() as { port: number }).port
const res = await fetch(`http://localhost:${port}/`)
const body = await res.text()
console.log("status:", res.status, res.statusText)
process.stdout.write("corp: " + body)
server.close()
}
main()
Răspunsul cu JSON
Un handler de API face trei lucruri: setează antetul Content-Type, alege un cod de status și scrie datele. res.writeHead(200, { "Content-Type": "application/json" }) le face pe primele două, iar res.end(JSON.stringify(value)) scrie corpul.
Ordinea contează: statusul și antetele trebuie setate înainte de a se scrie corpul.
Un endpoint JSON
Handlerul transformă un UserRecord în text JSON și îl trimite. Clientul primește JSON valid și tipul de conținut corect — acesta este scheletul fiecărui endpoint din restul acestui grup.
Ieșire: program TypeScript și rezultatul capturat
import { createServer, type IncomingMessage, type ServerResponse } from "node:http"
interface UserRecord {
id: number
name: string
}
function userHandler(req: IncomingMessage, res: ServerResponse): void {
const user: UserRecord = { id: 1, name: "Ana" }
// Mai întâi antetele și statusul, apoi corpul.
res.writeHead(200, { "Content-Type": "application/json" })
res.end(JSON.stringify(user))
}
async function main(): Promise<void> {
const server = createServer(userHandler)
await new Promise<void>(resolve => server.listen(0, () => resolve()))
const port = (server.address() as { port: number }).port
const res = await fetch(`http://localhost:${port}/user`)
const body = await res.text()
console.log("status:", res.status, res.statusText)
console.log("tip: ", res.headers.get("content-type"))
console.log("corp: ", body)
server.close()
}
main()