NestJS
Quick Start
import { Controller, Get, Module, NestFactory } from '@nestjs/common';
@Controller('health') class HealthController { @Get() check() { return { status: 'ok' }; } }
@Module({ controllers: [HealthController] }) class AppModule {}
async function bootstrap() { const app = await NestFactory.create(AppModule); await app.listen(3000); } bootstrap();
Features
Feature Description Guide
Modules Dependency injection, providers MODULES.md
Controllers Routes, validation, guards CONTROLLERS.md
Services Business logic, repositories SERVICES.md
Database TypeORM, Prisma integration DATABASE.md
Auth Passport, JWT, guards AUTH.md
Testing Unit, e2e with Jest TESTING.md
Common Patterns
Controller with Validation
@Controller('users') @UseGuards(JwtAuthGuard) export class UsersController { constructor(private readonly usersService: UsersService) {}
@Get() @Roles('admin') findAll(@Query() query: PaginationDto) { return this.usersService.findAll(query); }
@Get(':id') findOne(@Param('id', ParseUUIDPipe) id: string) { return this.usersService.findOne(id); }
@Post() create(@Body() dto: CreateUserDto) { return this.usersService.create(dto); } }
Service with Repository
@Injectable() export class UsersService { constructor(private readonly usersRepo: UsersRepository) {}
async findAll(query: PaginationDto) { const [users, total] = await this.usersRepo.findAllWithCount({ skip: query.skip, take: query.limit, }); return { data: users, total, page: query.page }; }
async findOne(id: string) { const user = await this.usersRepo.findOne({ where: { id } }); if (!user) throw new NotFoundException('User not found'); return user; }
async create(dto: CreateUserDto) { const exists = await this.usersRepo.findByEmail(dto.email); if (exists) throw new ConflictException('Email in use'); return this.usersRepo.save(this.usersRepo.create(dto)); } }
DTO with Validation
export class CreateUserDto { @IsEmail() email: string;
@IsString() @MinLength(2) name: string;
@IsString() @MinLength(8) @Matches(/^(?=.[A-Z])(?=.\d)/, { message: 'Password must contain uppercase and number', }) password: string;
@IsOptional() @IsEnum(UserRole) role?: UserRole; }
Workflows
API Development
-
Create module with nest g module [name]
-
Create controller and service
-
Define DTOs with class-validator
-
Add guards for auth/roles
-
Write unit and e2e tests
Module Structure
@Module({ imports: [TypeOrmModule.forFeature([User])], controllers: [UsersController], providers: [UsersService, UsersRepository], exports: [UsersService], }) export class UsersModule {}
Best Practices
Do Avoid
Use dependency injection Direct instantiation
Validate with DTOs Trusting input
Use guards for auth Auth logic in controllers
Use interceptors for cross-cutting Duplicating logging/transform
Write unit + e2e tests Skipping test coverage
Project Structure
src/ ├── main.ts ├── app.module.ts ├── common/ │ ├── decorators/ │ ├── guards/ │ ├── interceptors/ │ └── pipes/ ├── config/ ├── users/ │ ├── users.module.ts │ ├── users.controller.ts │ ├── users.service.ts │ ├── dto/ │ └── entities/ └── auth/ ├── auth.module.ts ├── strategies/ └── guards/
For detailed examples and patterns, see reference files above.