Getting Started

Installation

Install NextRush in under five minutes — one package, one command, one running server — then verify it end to end.

Start here

Install NextRush in under five minutes.

One package. One command. One running server.

~5 minNode 22+TypeScriptNode · Bun · Deno · Edge
  1. Choose
  2. Install
  3. Verify
  4. Done

Choose your path

Two paths reach the same running server — both install the same nextrush package; the scaffolder automates the folder and config around it. If you're unsure, scaffold — you can still read every file it produces afterward.

★ Recommended

Create a new project

One command wires routing, middleware, scripts, and your chosen style — functional, class-based, or full — with create-nextrush.

Use this →

Existing project

Add nextrush to a project you already have, or wire each piece yourself to see how it fits together.

Install manually →

Requirements

Three things, and you're set:

✓ Node.js 22+
✓ ESM project
✓ TypeScript

Only curious? Open these.

NextRush targets ES2022 and stable ESM throughout — there's no CommonJS build for any @nextrush/* package. Node 22 is the oldest LTS line where that target lands cleanly, so it's the floor every adapter and example assumes. NextRush declares "engines": { "node": ">=22.0.0" } in every published package. See the FAQ for the full reasoning.

NextRush publishes ESM only, with no CommonJS build to fall back to. That's why your package.json needs "type": "module" before anything runs — and it explains the one-line setup in the next section. Installing on Bun, Deno, or the edge instead? See Runtimes.

Install

Create the project folder

mkdir my-api && cd my-api
pnpm init

Add "type": "module" to the generated package.json. NextRush is ESM-only — there's no CommonJS build to fall back to — so Node needs to know your .ts/.js files are ES modules before anything else runs.

Expected result — the folder appears with a package.json containing "type": "module".

Install NextRush

$ pnpm add nextrush
$ pnpm add -D tsx typescript @types/node

Expected result — nextrush (and the dev tooling) added to your package.json.

Write a server and run it

Create src/index.ts:

src/index.ts
import { createApp, createRouter, listen } from 'nextrush';

const app = createApp();
const router = createRouter();

router.get('/', (ctx) => {
  ctx.json({ status: 'ok', framework: 'NextRush' });
});

app.route('/', router);
await listen(app, 8080);

Run it:

npx tsx src/index.ts

Expected result — a JSON response at http://localhost:8080: {"status": "ok", "framework": "NextRush"}.

Installed — you have everything you need. Let's verify it end to end.

  • nextrush is the meta-package — one install re-exports @nextrush/core, @nextrush/router, @nextrush/adapter-node, @nextrush/errors, and @nextrush/types. Nothing else to add.
  • createApp() builds the application, createRouter() gives you a router to attach routes to, app.route('/', router) mounts it, and listen(app, 8080) starts the Node adapter.
  • tsx runs the TypeScript entry directly — no separate compile pass.

ctx.json() sends JSON responses automatically, but reading an incoming JSON request body is not. To handle a POST (or any body-bearing request) you must add a body parser — otherwise ctx.body stays undefined and the body is silently ignored.

Install it, then register it before your routes:

pnpm add @nextrush/body-parser
src/index.ts
import { createApp, createRouter, listen } from 'nextrush';
import { bodyParser } from '@nextrush/body-parser'; // combined: JSON + urlencoded

const app = createApp();
const router = createRouter();

app.use(bodyParser()); // ← parse incoming bodies before routes run

router.post('/tasks', (ctx) => {
  const body = ctx.body as { title?: string }; // ctx.body is typed unknown
  ctx.json({ saved: body.title });
});

app.route('/', router);
await listen(app, 8080);

Only need JSON, with tighter limits? Swap the combined parser for the single json parser — same shape: import, register, read.

src/index.ts
import { createApp, createRouter, listen } from 'nextrush';
import { json } from '@nextrush/body-parser';

const app = createApp();
const router = createRouter();

app.use(json({ limit: '10mb', strict: true }));

router.post('/tasks', (ctx) => {
  const body = ctx.body as { title?: string };
  ctx.json({ saved: body.title });
});

app.route('/', router);
await listen(app, 8080);

bodyParser() skips bodyless methods (GET/HEAD/DELETE/OPTIONS), enforces a 1 MB default limit, and rejects invalid JSON with a 400. Full options: Body parser.

NextRush ships full type definitions. This tsconfig.json matches what the framework's own examples and CI run against:

tsconfig.json
{
  "compilerOptions": {
    "target": "ES2022",
    "module": "NodeNext",
    "moduleResolution": "NodeNext",
    "strict": true,
    "esModuleInterop": true,
    "skipLibCheck": true,
    "types": ["node"],
    "outDir": "dist",
    "rootDir": "src"
  },
  "include": ["src"]
}

Only using class-based controllers? Add "experimentalDecorators": true and "emitDecoratorMetadata": true to compilerOptions if you import from nextrush/class — that entry point auto-imports reflect-metadata itself. See Class-based controllers.

Verify

Two checks prove the install end to end — runtime version, then the server responds.

✓ Node.js 22
✓ Package installed
✓ Server running
✓ JSON response
node --version
# → v22.x.x or newer

If node --version reports below 22, install a newer version before continuing — NextRush's adapters and examples aren't tested against older lines, and installs may warn or fail depending on your package manager's engines enforcement.

curl http://localhost:8080/
# → {"status":"ok","framework":"NextRush"}

🎉 Installation complete

Your request completed the full request path — the same one every NextRush app runs.

  1. Application
  2. Router
  3. Handler
  4. Response

Common issues

Most installation issues fall into these three categories.

Cause: an older Node install or version-manager default.

Fix: install or select Node 22 or newer before running pnpm add nextrush — the framework's engines field expects it everywhere.

Cause: package.json is missing "type": "module", so Node tries to load ESM output as CommonJS.

Fix: add "type": "module" — NextRush publishes no CommonJS build for any package to fall back to.

Cause: importing nextrush/class without experimentalDecorators / emitDecoratorMetadata enabled in tsconfig.json.

Fix: add both compiler options — the reflect-metadata import itself is already handled for you.

Next step

🚀 Task API Tutorial — recommended · ~20 min

The hands-on tutorial: routing, a JSON body, and a real 404 — starting from exactly where this page leaves off. Start the tutorial →

Optional: developer toolkit

🧰 @nextrush/dev

Most developers install this right after setup. Everything above ran without it — @nextrush/dev is a dev-only CLI, not a dependency your server needs — but it makes the loop from here on noticeably faster:

  • Hot-reload dev server (nextrush dev)
  • Production builds (nextrush build)
  • Code generators for controllers, services, middleware, guards, and routes
pnpm add -D @nextrush/dev

Optional. Install it only if you want a better day-to-day workflow — nothing on this page or the next tutorial requires it.

When you're ready to deploy, see the production guide for runtime pinning, dependency trimming, and per-platform setup — that's a deployment concern, not an install one.

Now build something.

Was this helpful?

On this page