
关于
NestJS 架构模式,涵盖模块、控制器、提供者、DTO 验证、守卫、拦截器、配置管理和生产级 TypeScript 后端。
name: nestjs-patterns description: NestJS 架构模式,涵盖模块、控制器、提供者、DTO 验证、守卫、拦截器、配置和生产级 TypeScript 后端。 origin: ECC
NestJS 开发模式
用于模块化 TypeScript 后端的生产级 NestJS 模式。
何时激活
- 构建 NestJS API 或服务
- 组织模块、控制器和提供者
- 添加 DTO 验证、守卫、拦截器或异常过滤器
- 配置环境感知设置和数据库集成
- 测试 NestJS 单元或 HTTP 端点
项目结构
src/
├── app.module.ts
├── main.ts
├── common/
│ ├── filters/
│ ├── guards/
│ ├── interceptors/
│ └── pipes/
├── config/
│ ├── configuration.ts
│ └── validation.ts
├── modules/
│ ├── auth/
│ │ ├── auth.controller.ts
│ │ ├── auth.module.ts
│ │ ├── auth.service.ts
│ │ ├── dto/
│ │ ├── guards/
│ │ └── strategies/
│ └── users/
│ ├── dto/
│ ├── entities/
│ ├── users.controller.ts
│ ├── users.module.ts
│ └── users.service.ts
└── prisma/ or database/
- 将领域代码保留在功能模块内。
- 将跨切面的过滤器、装饰器、守卫和拦截器放在
common/中。 - 将 DTO 放在拥有它们的模块附近。
引导和全局验证
async function bootstrap() {
const app = await NestFactory.create(AppModule, { bufferLogs: true });
app.useGlobalPipes(
new ValidationPipe({
whitelist: true,
forbidNonWhitelisted: true,
transform: true,
transformOptions: { enableImplicitConversion: true },
}),
);
app.useGlobalInterceptors(new ClassSerializerInterceptor(app.get(Reflector)));
app.useGlobalFilters(new HttpExceptionFilter());
await app.listen(process.env.PORT ?? 3000);
}
bootstrap();
- 在公共 API 上始终启用
whitelist和forbidNonWhitelisted。 - 优先使用一个全局验证管道,而非在每个路由重复验证配置。
模块、控制器和提供者
@Module({
controllers: [UsersController],
providers: [UsersService],
exports: [UsersService],
})
export class UsersModule {}
@Controller('users')
export class UsersController {
constructor(private readonly usersService: UsersService) {}
@Get(':id')
getById(@Param('id', ParseUUIDPipe) id: string) {
return this.usersService.getById(id);
}
@Post()
create(@Body() dto: CreateUserDto) {
return this.usersService.create(dto);
}
}
@Injectable()
export class UsersService {
constructor(private readonly usersRepo: UsersRepository) {}
async create(dto: CreateUserDto) {
return this.usersRepo.create(dto);
}
}
- 控制器应保持精简:解析 HTTP 输入、调用提供者、返回响应 DTO。
- 将业务逻辑放在可注入服务中,而非控制器。
- 只导出其他模块真正需要的提供者。
DTO 和验证
export class CreateUserDto {
@IsEmail()
email!: string;
@IsString()
@Length(2, 80)
name!: string;
@IsOptional()
@IsEnum(UserRole)
role?: UserRole;
}
- 使用
class-validator验证每个请求 DTO。 - 使用专用响应 DTO 或序列化器,而非直接返回 ORM 实体。
- 避免泄露内部字段如密码哈希、令牌或审计列。
认证、守卫和请求上下文
@UseGuards(JwtAuthGuard, RolesGuard)
@Roles('admin')
@Get('admin/report')
getAdminReport(@Req() req: AuthenticatedRequest) {
return this.reportService.getForUser(req.user.id);
}
- 除非真正共享,否则将认证策略和守卫保持在模块本地。
- 在守卫中编码粗粒度访问规则,然后在服务中进行资源特定的授权。
- 对已认证请求对象优先使用显式请求类型。
异常过滤器和错误格式
@Catch()
export class HttpExceptionFilter implements ExceptionFilter {
catch(exception: unknown, host: ArgumentsHost) {
const ctx = host.switchToHttp();
const response = ctx.getResponse();
const status = exception instanceof HttpException
? exception.getStatus()
: HttpStatus.INTERNAL_SERVER_ERROR;
response.status(status).json({
statusCode: status,
message: exception instanceof HttpException
? exception.message
: 'Internal server error',
timestamp: new Date().toISOString(),
});
}
}
- 返回一致的错误形状以便客户端解析。
- 在生产环境中记录完整异常但只向客户端暴露安全消息。
兼容工具
Claude CodeCursor
标签
后端开发

