nestjs-project-structure
March 15, 2026 ยท View on GitHub
Node.js framework NestJS project structure
Started from this issue: nestjs/nest#2249
Alternatives
This example is based on the modules recommended by the NestJS official documentation as default (introduced at the top of the section).
If you focus on the performance or features of the module, you can consider:
- Fastify instead of
Express - MikroORM instead of
TypeORM- or DrizzleORM
- or Sequelize
- or Prisma
- SWC instead of
TypeScript compiler - Vitest instead of
Jest - ESM instead of
CommonJS
Check out the nestjs-project-performance repository for examples using this alternative.
Configuration
- Create a
.envfile- Rename the .env.sample file to
.envto fix it.
- Rename the .env.sample file to
- Edit env config
- Edit the file in the config/envs folder.
default,development,production,test
Installation
# 1. node_modules
npm ci
# 2. When synchronize database from existing entities
npm run entity:sync
# 2-1. When import entities from an existing database
npm run entity:load
If you use multiple databases in entity:load, modify them.
Development
npm run start:dev
# https://docs.nestjs.com/recipes/repl
npm run start:repl
Test
npm test # exclude e2e
npm run test:e2e
Production
npm run lint
npm run build
# define environment variable yourself.
# NODE_ENV=production PORT=8000 NO_COLOR=true node dist/app
node dist/app
# OR
npm start
Folders
+-- bin // Custom tasks
+-- dist // Source build
+-- public // Static Files
+-- src
| +-- config // Environment Configuration
| +-- entity // TypeORM Entities
| +-- auth // Authentication
| +-- common // Global Nest Module
| | +-- constants // Constant value and Enum
| | +-- controllers // Nest Controllers
| | +-- decorators // Nest Decorators
| | +-- dto // DTO (Data Transfer Object) Schema, Validation
| | +-- filters // Nest Filters
| | +-- guards // Nest Guards
| | +-- interceptors // Nest Interceptors
| | +-- interfaces // TypeScript Interfaces
| | +-- middleware // Nest Middleware
| | +-- pipes // Nest Pipes
| | +-- providers // Nest Providers
| | +-- * // models, repositories, services...
| +-- shared // Shared Nest Modules
| +-- gql // GraphQL Structure
| +-- * // Other Nest Modules, non-global, same as common structure above
+-- test // Jest testing
+-- typings // Modules and global type definitions
// Module structure
// Add folders according to module scale. If it's small, you don't need to add folders.
+-- src/greeter
| +-- * // folders
| +-- greeter.constant.ts
| +-- greeter.controller.ts
| +-- greeter.service.ts
| +-- greeter.module.ts
| +-- greeter.*.ts
| +-- index.ts
This is the most basic structure to start a NestJS project.
You should choose the right architecture[1] (Layered, Clean, Onion, Hexagonal ...)[2] based on the size of your project.
Implements
- Refer to bootstrap, app.module
- Database, Module Router, Static Files, Validation, Pino Logger
- Global Exception Filter
- Global Logging Context Middleware
- Custom Logger with nestjs-pino
- Custom Decorators Example at Nest level
- Configuration
- Authentication - JWT and Session login with Passport
- Role-based Guard
- Controller Routes
- Auth Login
- Sample Parameter and DTO
- CRUD API Sample
- Database Query Example
- Unit Test
- E2E Test
- Shared Modules Example
- GraphQL Structure Example
Documentation
# APP, Compodoc
npm run doc #> http://localhost:8080
# API, Swagger - src/swagger.ts
npm run doc:api #> http://localhost:8000/api
File Naming for Class
export class PascalCaseSuffix {} //= pascal-case.suffix.ts
// Except for suffix, PascalCase to hyphen-case
class FooBarNaming {} //= foo-bar.naming.ts
class FooController {} //= foo.controller.ts
class BarQueryDto {} //= bar-query.dto.ts
Interface Naming
// https://stackoverflow.com/questions/541912
// https://stackoverflow.com/questions/2814805
interface User {}
interface CustomeUser extends User {}
interface ThirdCustomeUser extends CustomeUser {}
Index Exporting
# It is recommended to place index.ts in each folder and export.
# Unless it's a special case, it is import from a folder instead of directly from a file.
- import { FooController } from './controllers/foo.controller';
- import { BarController } from './controllers/bar.controller';
+ import { FooController, BarController } from './controllers';
# My preferred method is to place only one fileOrFolder name at the end of the path.
- import { UtilService } from '../common/providers/util.service';
+ import { UtilService } from '../common';
Warning
Barrel files may need to be avoided in frontend or serverless environments.
Learn more: Why avoid barrel files?
Circular dependency
https://docs.nestjs.com/fundamentals/circular-dependency
# Do not use a path that ends with a dot.
- import { FooService } from '.';
- import { BarService } from '..';
+ import { FooService } from './foo.service';
+ import { BarService } from '../providers';