Nest实践
nestjs-best-practices
by giuseppe-trisciuoglio
聚焦生产级NestJS开发规范,覆盖模块边界、依赖注入作用域、异常过滤器、DTO校验与Drizzle ORM集成,适合架构设计、重构评审和团队统一代码风格。
安装
claude skill add --url github.com/giuseppe-trisciuoglio/developer-kit/tree/main/plugins/developer-kit-typescript/skills/nestjs-best-practices文档
NestJS Best Practices
Overview
This skill provides a curated set of best practices for building production-grade NestJS applications. All guidelines are grounded in the Official NestJS Documentation and enforce consistent, maintainable, and scalable patterns.
When to Use
- Designing or refactoring NestJS module architecture
- Implementing dependency injection with custom or scoped providers
- Creating exception filters and standardizing error responses
- Validating DTOs with
class-validatorandValidationPipe - Integrating Drizzle ORM within NestJS providers
- Reviewing NestJS code for architectural anti-patterns
- Onboarding new developers to a NestJS codebase
Instructions
1. Modular Architecture
Follow strict module encapsulation. Each domain feature should be its own @Module():
- Export only what other modules need — keep internal providers private
- Use
forwardRef()only as a last resort for circular dependencies; prefer restructuring - Group related controllers, services, and repositories within the same module
- Use a
SharedModulefor cross-cutting concerns (logging, configuration, caching)
See references/arch-module-boundaries.md for enforcement rules.
2. Dependency Injection
Choose the correct provider scope based on use case:
| Scope | Lifecycle | Use Case |
|---|---|---|
DEFAULT | Singleton (shared) | Stateless services, repositories |
REQUEST | Per-request instance | Request-scoped data (tenant, user context) |
TRANSIENT | New instance per injection | Stateful utilities, per-consumer caches |
- Default to
DEFAULTscope — only useREQUESTorTRANSIENTwhen justified - Use constructor injection exclusively — avoid property injection
- Register custom providers with
useClass,useValue,useFactory, oruseExisting
See references/di-provider-scoping.md for enforcement rules.
3. Request Lifecycle
Understand and respect the NestJS request processing pipeline:
Middleware → Guards → Interceptors (before) → Pipes → Route Handler → Interceptors (after) → Exception Filters
- Middleware: Cross-cutting concerns (logging, CORS, body parsing)
- Guards: Authorization and authentication checks (return
true/false) - Interceptors: Transform response data, add caching, measure timing
- Pipes: Validate and transform input parameters
- Exception Filters: Catch and format error responses
4. Error Handling
Standardize error responses across the application:
- Extend
HttpExceptionfor HTTP-specific errors - Create domain-specific exception classes (e.g.,
OrderNotFoundException) - Implement a global
ExceptionFilterfor consistent error formatting - Use the Result pattern for expected business logic failures
- Never silently swallow exceptions
See references/error-exception-filters.md for enforcement rules.
5. Validation
Enforce input validation at the API boundary:
- Enable
ValidationPipeglobally withtransform: trueandwhitelist: true - Decorate all DTO properties with
class-validatordecorators - Use
class-transformerfor type coercion (@Type(),@Transform()) - Create separate DTOs for Create, Update, and Response operations
- Never trust raw user input — validate everything
See references/api-validation-dto.md for enforcement rules.
6. Database Patterns (Drizzle ORM)
Integrate Drizzle ORM following NestJS provider conventions:
- Wrap the Drizzle client in an injectable provider
- Use the Repository pattern for data access encapsulation
- Define schemas in dedicated schema files per domain module
- Use transactions for multi-step operations
- Keep database logic out of controllers
See references/db-drizzle-patterns.md for enforcement rules.
Best Practices
| Area | Do | Don't |
|---|---|---|
| Modules | One module per domain feature | Dump everything in AppModule |
| DI Scoping | Default to singleton scope | Use REQUEST scope without justification |
| Error Handling | Custom exception filters + domain errors | Bare try/catch with console.log |
| Validation | Global ValidationPipe + DTO decorators | Manual if checks in controllers |
| Database | Repository pattern with injected client | Direct DB queries in controllers |
| Testing | Unit test services, e2e test controllers | Skip tests or test implementation details |
| Configuration | @nestjs/config with typed schemas | Hardcode values or use process.env |
Examples
Example 1: Creating a New Domain Module
When building a new "Product" feature:
// product/product.module.ts
@Module({
imports: [DatabaseModule],
controllers: [ProductController],
providers: [ProductService, ProductRepository],
exports: [ProductService],
})
export class ProductModule {}
Example 2: DTO with Full Validation
// product/dto/create-product.dto.ts
import { IsString, IsNumber, IsPositive, MaxLength } from 'class-validator';
export class CreateProductDto {
@IsString()
@MaxLength(255)
readonly name: string;
@IsNumber()
@IsPositive()
readonly price: number;
}
Example 3: Service with Proper Error Handling
@Injectable()
export class ProductService {
constructor(private readonly productRepository: ProductRepository) {}
async findById(id: string): Promise<Product> {
const product = await this.productRepository.findById(id);
if (product === null) {
throw new ProductNotFoundException(id);
}
return product;
}
}
Constraints and Warnings
- Do not mix scopes without justification —
REQUEST-scoped providers cascade to all dependents - Never access database directly from controllers — always go through service and repository layers
- Avoid
forwardRef()— restructure modules to eliminate circular dependencies - Do not skip
ValidationPipe— always validate at the API boundary with DTOs - Never hardcode secrets — use
@nestjs/configwith environment variables - Keep modules focused — one domain feature per module, avoid "god modules"
References
references/architecture.md— Deep-dive into NestJS architectural patternsreferences/— Individual enforcement rules with correct/incorrect examplesassets/templates/— Starter templates for common NestJS components
相关 Skills
资深数据工程师
by alirezarezvani
聚焦生产级数据工程,覆盖 ETL/ELT、批处理与流式管道、数据建模、Airflow/dbt/Spark 优化和数据质量治理,适合设计数据架构、搭建现代数据栈与排查性能问题。
✎ 复杂数据管道、ETL/ELT 和治理难题交给它,凭 Spark、Airflow、dbt 等现代数据栈经验,能更稳地搭起可扩展的数据基础设施。
技术栈评估
by alirezarezvani
对比框架、数据库和云服务,结合 5 年 TCO、安全风险、生态活力与迁移复杂度做量化评估,适合技术选型、栈升级和替换路线决策。
✎ 帮你系统比较技术栈优劣,不只看功能,还把TCO、安全性和生态健康度一起量化,选型和迁移决策更稳。
迁移架构师
by alirezarezvani
为数据库、API 与基础设施迁移制定分阶段零停机方案,提前校验兼容性与风险,生成回滚策略、验证关卡和时间线,适合复杂系统平滑切换。
✎ 做数据库与存储迁移时,用它统一梳理表结构和数据搬迁流程,架构视角更完整,复杂迁移也更稳。
相关 MCP 服务
SQLite 数据库
编辑精选by Anthropic
SQLite 是让 AI 直接查询本地数据库进行数据分析的 MCP 服务器。
✎ 这个服务器解决了 AI 无法直接访问 SQLite 数据库的问题,适合需要快速分析本地数据集的开发者。不过,作为参考实现,它可能缺乏生产级的安全特性,建议在受控环境中使用。
PostgreSQL 数据库
编辑精选by Anthropic
PostgreSQL 是让 Claude 直接查询和管理你的数据库的 MCP 服务器。
✎ 这个服务器解决了开发者需要手动编写 SQL 查询的痛点,特别适合数据分析师或后端开发者快速探索数据库结构。不过,由于是参考实现,生产环境使用前务必评估安全风险,别指望它能处理复杂事务。
Firecrawl 智能爬虫
编辑精选by Firecrawl
Firecrawl 是让 AI 直接抓取网页并提取结构化数据的 MCP 服务器。
✎ 它解决了手动写爬虫的麻烦,让 Claude 能直接访问动态网页内容。最适合需要实时数据的研究者或开发者,比如监控竞品价格或抓取新闻。但要注意,它依赖第三方 API,可能涉及隐私和成本问题。