NestJS is a Node.js framework written in TypeScript that gives your backend a clear structure, so it doesn’t get messy as it grows. Think of it as organized scaffolding on top of Express (the default) or Fastify.
Node.js, NestJS, Java Backend Engineer
If you've built a few Node.js APIs with Express, you probably know the feeling. The first 200 lines are fun. By line 2,000 you're staring at a pile of routes and helper files, wondering where anything is supposed to live.
That's the exact itch NestJS scratches.
NestJS is a framework for building server-side apps with Node.js. It's written in TypeScript, and it gives you a clear structure from the first minute, so your project doesn't turn into a junk drawer as it grows. This guide walks through the official "first steps" setup in plain language: what you need installed, how to create a project, what every generated file does, and how to run the thing.
No theory dump. Just the stuff you need to get a server answering requests.
NestJS (people also just say "Nest") is an opinionated backend framework. It runs on Node.js, uses TypeScript by default, and sits on top of an HTTP server library, Express by default or Fastify if you prefer. Where Express says "do whatever you want," Nest says "here's a sensible way to organize this." If you've used Angular, a lot of the ideas will feel familiar, but you don't need any Angular background to follow along.
Not strictly. Nest supports both TypeScript and plain JavaScript. The catch is that Nest leans on newer language features, so if you go the plain JavaScript route you'll need Babel in the mix.
Honestly, most people just use TypeScript, and almost every example in the official docs is written that way. If you're on the fence, go with TypeScript. You'll fight the tooling less.
You need Node.js installed. That's really it, but the version matters.
nest new and nest generate) are pickier. They need v22.22.3+, v24.15+, or v26+.The simplest fix is to install the latest active LTS release of Node. That covers both requirements, and you can stop thinking about it. Run node -v n your terminal if you're not sure what you have.
npm i -g @nestjs/clinest new project-nameSwap project-name for whatever you're building. The CLI will ask you a couple of questions along the way.
You can choose ESM (the default) or CommonJS. This choice also decides your test runner. ESM projects use Vitest, and CommonJS projects use Jest. If you don't have a strong reason to pick CommonJS, stay with the default.
This is the official observability platform for Nest. Say yes and your project comes with the @nestjs/observe SDK already wired in, and the CLI can offer to link the project to your account once dependencies are installed. In an interactive terminal the prompt defaults to yes. In CI or any non-interactive environment it's skipped. If you want to avoid the prompt entirely, pass --observe or --no-observe. For a first project you're just learning on, "no" is perfectly fine, and you can link later with npx @nestjs/observe link.
One more detail worth knowing: new projects are generated with TypeScript's strict mode switched on. That catches more mistakes early. If it ever gets in your way while you're experimenting, you can set "strict": false in tsconfig.json, though I'd leave it on and get used to it.
When the CLI finishes, it has created your project folder, installed the dependencies, added some boilerplate, and filled a src/ directory with the core files.
src/Open the folder and you'll see five files:
src/ app.controller.spec.ts app.controller.ts app.module.ts app.service.ts main.tsHere's what each one does:
| File | What it's for |
|---|---|
app.controller.ts | A basic controller with one route |
app.controller.spec.ts | Unit tests for that controller |
app.module.ts | The root module of your app |
app.service.ts | A basic service with a single method |
main.ts |
Think of it like this. The controller receives a request. The service holds the logic. The module ties pieces together so Nest knows they belong to the same feature. As your app grows, the CLI's convention is to give each module its own folder, which keeps things easy to find months later.
main.ts file explainedmain.ts is where the app actually starts. It's short enough to read in one go:
import { NestFactory } from '@nestjs/core';import { AppModule } from './app.module.js';async function bootstrap() { const app = await NestFactory.create(AppModule); await app.listen(process.env.PORT ?? 3000);}await bootstrap();Walking through it: NestFactory comes from @nestjs/core and is what builds your application. The create() method takes your root module and hands back an app object. Then listen() starts an HTTP server on port 3000, or on whatever PORT is set to in your environment.
A small thing that's easy to miss: if something goes wrong while the app is being created, the process exits with code 1 by default. If you'd rather have the error thrown so you can handle it yourself, pass { abortOnError: false } to NestFactory.create().
Nest doesn't care much which HTTP library sits underneath. It's built to be platform-agnostic, and two are supported out of the box:
Each one has its own app type: NestExpressApplication and NestFastifyApplication. You only need to pass the type when you want to use methods specific to that platform:
const app = await NestFactory.create<NestExpressApplication>(AppModule);If you're just following a tutorial, skip this. Express works and you can revisit it later.
From the project folder:
npm run startThen open http://localhost:3000/ in your browser. You should see Hello World!. That's your first NestJS server, up and answering requests. Want it to reload whenever you save a file? Use watch mode instead:
npm run start:devThis recompiles and restarts the server on every change, which is what you'll use 95% of the time while building.
If builds feel slow, there's an option worth trying. Nest supports the SWC compiler, and you can use it by passing a flag:
npm run start -- -b swcRunning npm run start:dev on your laptop is fine for learning. At some point, though, you'll want your API online where other people can reach it.
Because Nest runs on Node.js, you need a server where you can install Node and keep a process running all the time. That's why a VPS makes more sense here than basic shared hosting, which is usually built for PHP sites and doesn't give you that kind of control.
I use Verpex VPS Hosting for this. Their unmanaged Linux VPS gives you full root access, so you pick the operating system, install the Node version you want, and set up the stack yourself. The plans run on NVMe SSD storage with dedicated resources (so you're not sharing your slice with a noisy neighbour), and there's a 99.9% uptime SLA plus round-the-clock infrastructure support. A small plan is plenty for a first NestJS project, and you can move up later if your traffic grows.
One honest warning: "unmanaged" means exactly that. Updates, firewall rules and security are your job, not theirs. If you've never touched a Linux server before, expect a bit of a learning curve. If you're comfortable with SSH and a terminal, that freedom is the whole point.
A typical first deploy looks like this: connect over SSH, install Node.js, clone your project, run npm install and npm run build, then keep it alive with a process manager like PM2.
Disclosure: this is an affiliate link. If you sign up through it, I may earn a commission at no extra cost to you.
You don't have to set up a linter yourself. TypeScript projects generated by the CLI ship with oxlint (the linter) and Prettier (the formatter) already installed. If you're not sure how they differ: the linter catches likely bugs and bad patterns, while the formatter only deals with how your code looks.
There are ready-made scripts for both, which is handy in CI and Git hooks where there's no IDE doing it for you:
npm run lintnpm run formatOne heads-up if you're following older tutorials. Many of them mention ESLint and Jest as the defaults. The current official setup uses oxlint, and a choice between Vitest and Jest depending on your module system, so don't panic if your generated project looks a little different from a 2022 blog post.
It's friendlier than its reputation. There are more concepts up front than Express (controllers, services, modules), but they pay off quickly once your project has more than a handful of routes. If you already know basic TypeScript, you'll be fine.
They're not really opponents. Nest uses Express under the hood by default. Express gives you a minimal toolkit, and Nest gives you structure on top of it. Small script or tiny API? Express alone is fine. Larger app, a team, or something you'll maintain for years? Nest's structure helps a lot.
REST APIs are the common starting point, but the framework also covers GraphQL, WebSockets, and microservices, so you won't outgrow it quickly.
The latest active LTS. It meets the requirements for running Nest and for the CLI generators.
You've got a running project and a rough map of what's in it. The natural next stops, in order, are:
Once those click, the rest of the framework (validation, authentication, databases) is mostly about plugging things into a structure you already understand.
Learn how NestJS controllers work. Routes, @Get and @Post, route params, query params, request body, status codes and a full CRUD example.
React is a front-end JavaScript library. React was developed by the Facebook Software Engineer Jordan Walke. React is a tool, for building UI components.
| The entry point; creates the Nest app instance |