Files
trackgo-be/.cursor/rules/nestjs-swagger.mdc
T
shancheas 0550cbe764 Implement pagination response handling and related enhancements
- Introduced `@Pagination()` decorator to mark list endpoints for pagination.
- Added `TransformInterceptor` to wrap responses in a standardized format `{ data, meta }`.
- Created pagination-related utility functions and constants for managing pagination logic.
- Defined `PaginationQueryDto` for handling pagination query parameters.
- Established `PaginationMetaDto` for OpenAPI documentation of pagination metadata.
- Updated existing controller and service structures to support pagination in responses.
- Added unit tests for pagination utilities and interceptor to ensure correct functionality.
2026-08-21 15:56:54 +07:00

80 lines
2.7 KiB
Plaintext
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
---
description: NestJS OpenAPI/Swagger conventions for controllers and DTOs
globs: "src/**/*.controller.ts,src/**/dto/**/*.ts,src/common/swagger/**/*.ts,src/main.ts,nest-cli.json"
alwaysApply: false
---
# NestJS Swagger Best Practices
## Controllers
Document every HTTP handler:
```typescript
@ApiTags('auth')
@Controller('auth')
export class AuthController {
@Post('login')
@ApiOperation({ summary: 'Log in' })
@ApiOkResponse({ type: TokenPairDto })
login(@Body() dto: LoginDto) { /* ... */ }
@Get('me')
@ApiBearerAuth('access-token')
@ApiOkResponse({ type: MeResponseDto })
me(@CurrentUser() user: AuthUser) { /* ... */ }
}
```
- Use `@ApiTags`, `@ApiOperation`, and typed `@ApiOkResponse` / `@ApiCreatedResponse` / `@ApiNoContentResponse`
- Response types must be DTO **classes**, not interfaces or domain entities
- Add `@ApiBearerAuth('access-token')` only on JWT-protected routes
- Public (`@Public()`) routes must omit bearer auth
- Document expected errors (`@ApiBadRequestResponse`, `@ApiUnauthorizedResponse`, etc.) when meaningful
### Paginated list endpoints
- Mark with `@Pagination()`; document the **public** envelope `{ data, meta }`, not the handlers `{ data, total }`
- Use a response DTO class for list items plus `PaginationMetaDto` from `src/common/http/response/`
- Detail / create / update / delete stay typed to the resource DTO (unwrapped)
```typescript
@Get()
@Pagination()
@ApiOperation({ summary: 'List shipments' })
@ApiOkResponse({
schema: {
properties: {
data: { type: 'array', items: { $ref: '#/components/schemas/ShipmentDto' } },
meta: { $ref: '#/components/schemas/PaginationMetaDto' },
},
},
})
list(@Query() query: ListShipmentsQueryDto): Promise<PaginationResponse<ShipmentDto>> {
return this.service.list(query)
}
```
## DTOs
- Request and response DTOs live under `dto/`
- Never expose domain entities or sensitive fields (`passwordHash`, secrets) in OpenAPI
- Nest CLI Swagger plugin is enabled — use `@ApiProperty` for examples, `format: 'password'`, `writeOnly`, not to restate every class-validator rule
- Examples must be fake; never real tokens or secrets
```typescript
// BAD — documents entity / real secret
@ApiOkResponse({ type: User })
@ApiProperty({ example: process.env.JWT_ACCESS_SECRET })
// GOOD — response DTO + fake example
@ApiOkResponse({ type: MeResponseDto })
@ApiProperty({ example: 'alice', format: 'password', writeOnly: true })
```
## Bootstrap
- Mount UI at `/docs` and JSON at `/docs-json` only (via `setupSwagger` / `configureApp`)
- Swagger is off when `NODE_ENV=production` unless `SWAGGER_ENABLED=true`
- Keep the `@nestjs/swagger` plugin in `nest-cli.json` (`classValidatorShim`, `introspectComments`, `dtoFileNameSuffix: [".dto.ts"]`)