123 lines
2.4 KiB
Plaintext
123 lines
2.4 KiB
Plaintext
|
|
---
|
|||
|
|
description: 后端特定的开发规范(仅作用于 backend 目录)
|
|||
|
|
globs:
|
|||
|
|
alwaysApply: true
|
|||
|
|
---
|
|||
|
|
|
|||
|
|
# 后端特定规范
|
|||
|
|
|
|||
|
|
本规则仅作用于 `backend/` 目录。
|
|||
|
|
|
|||
|
|
## NestJS 最佳实践
|
|||
|
|
|
|||
|
|
### 依赖注入
|
|||
|
|
|
|||
|
|
始终使用构造函数注入:
|
|||
|
|
|
|||
|
|
```typescript
|
|||
|
|
@Injectable()
|
|||
|
|
export class MyService {
|
|||
|
|
constructor(
|
|||
|
|
private readonly prisma: PrismaService,
|
|||
|
|
private readonly otherService: OtherService,
|
|||
|
|
) {}
|
|||
|
|
}
|
|||
|
|
```
|
|||
|
|
|
|||
|
|
### 全局模块
|
|||
|
|
|
|||
|
|
PrismaModule 已设为全局模块,无需在每个模块中导入。
|
|||
|
|
|
|||
|
|
### 环境变量
|
|||
|
|
|
|||
|
|
使用 `@nestjs/config` 的 ConfigService:
|
|||
|
|
|
|||
|
|
```typescript
|
|||
|
|
constructor(private configService: ConfigService) {
|
|||
|
|
const jwtSecret = this.configService.get<string>('JWT_SECRET');
|
|||
|
|
}
|
|||
|
|
```
|
|||
|
|
|
|||
|
|
## 测试规范
|
|||
|
|
|
|||
|
|
### 单元测试
|
|||
|
|
|
|||
|
|
```typescript
|
|||
|
|
describe('UsersService', () => {
|
|||
|
|
let service: UsersService;
|
|||
|
|
let prisma: PrismaService;
|
|||
|
|
|
|||
|
|
beforeEach(async () => {
|
|||
|
|
const module = await Test.createTestingModule({
|
|||
|
|
providers: [
|
|||
|
|
UsersService,
|
|||
|
|
{
|
|||
|
|
provide: PrismaService,
|
|||
|
|
useValue: mockPrismaService,
|
|||
|
|
},
|
|||
|
|
],
|
|||
|
|
}).compile();
|
|||
|
|
|
|||
|
|
service = module.get<UsersService>(UsersService);
|
|||
|
|
prisma = module.get<PrismaService>(PrismaService);
|
|||
|
|
});
|
|||
|
|
|
|||
|
|
it('should create a user', async () => {
|
|||
|
|
const dto = { username: 'test', password: 'pass123' };
|
|||
|
|
const result = await service.create(dto, 1);
|
|||
|
|
expect(result).toBeDefined();
|
|||
|
|
});
|
|||
|
|
});
|
|||
|
|
```
|
|||
|
|
|
|||
|
|
## 日志记录
|
|||
|
|
|
|||
|
|
使用 NestJS Logger:
|
|||
|
|
|
|||
|
|
```typescript
|
|||
|
|
import { Logger } from '@nestjs/common';
|
|||
|
|
|
|||
|
|
export class MyService {
|
|||
|
|
private readonly logger = new Logger(MyService.name);
|
|||
|
|
|
|||
|
|
async someMethod() {
|
|||
|
|
this.logger.log('执行某操作');
|
|||
|
|
this.logger.warn('警告信息');
|
|||
|
|
this.logger.error('错误信息', error.stack);
|
|||
|
|
}
|
|||
|
|
}
|
|||
|
|
```
|
|||
|
|
|
|||
|
|
## 常用脚本
|
|||
|
|
|
|||
|
|
```bash
|
|||
|
|
# 开发
|
|||
|
|
pnpm start:dev
|
|||
|
|
|
|||
|
|
# 数据库迁移
|
|||
|
|
pnpm prisma:migrate:dev
|
|||
|
|
|
|||
|
|
# 初始化管理员
|
|||
|
|
pnpm init:admin
|
|||
|
|
|
|||
|
|
# 初始化菜单
|
|||
|
|
pnpm init:menus
|
|||
|
|
```
|
|||
|
|
|
|||
|
|
## 项目结构
|
|||
|
|
|
|||
|
|
```
|
|||
|
|
src/
|
|||
|
|
├── auth/ # 认证模块
|
|||
|
|
├── users/ # 用户管理
|
|||
|
|
├── roles/ # 角色管理
|
|||
|
|
├── permissions/ # 权限管理
|
|||
|
|
├── menus/ # 菜单管理
|
|||
|
|
├── tenants/ # 租户管理
|
|||
|
|
├── school/ # 学校管理
|
|||
|
|
├── contests/ # 竞赛管理
|
|||
|
|
├── common/ # 公共模块
|
|||
|
|
├── prisma/ # Prisma 服务
|
|||
|
|
└── main.ts # 入口文件
|
|||
|
|
```
|