| name | backend-patterns |
| type | reference |
| description | Applies production backend patterns: middleware, error handling, auth, database integration, and API design. Use when working with backend service files or when the user mentions Express, Fastify, NestJS, backend patterns, or service architecture. |
| paths | ["**/*.ts","**/*.js","**/server.*","**/app.*","**/routes/**"] |
| effort | 3 |
| allowed-tools | Read, Glob, Grep, Write, Edit, Bash |
| context | fork |
| agent | backend-architect |
| user-invocable | true |
| when_to_use | When building Node.js backend services with Express, Fastify, or similar frameworks |
Backend Patterns
Critical rules (non-obvious)
- Always handle async errors in Express: unhandled promise rejections crash the process; use
express-async-errors or wrap every async handler
- Never trust
req.body size: set limit on body-parser; default 100kb is too large for some, too small for others
process.env access at import time: if accessed before dotenv.config(), value is undefined; call config() first in entry file
- Connection pool misconfiguration: default pool size (10) will exhaust under load; set
pool.max based on (num_cores * 2) + effective_spindle_count
res.json() after res.send(): causes "Cannot set headers after they are sent" — always return after sending response
Express: production setup
import express from "express";
import "express-async-errors";
import helmet from "helmet";
import { rateLimit } from "express-rate-limit";
const app = express();
app.use(helmet());
app.use(express.json({ limit: "10kb" }));
app.use(rateLimit({ windowMs: 15 * 60 * 1000, max: 100 }));
app.use(, userRouter);
app.(, productRouter);
app.( res.().({ : }));
app.( {
status = err ? err. : ;
res.(status).({ : err. });
});