212 lines
5.6 KiB
Markdown
212 lines
5.6 KiB
Markdown
# Development Guide
|
|
|
|
> **Note**: This guide provides comprehensive standards and workflows for contributing to the GoodGo Microservices Platform.
|
|
|
|
## Table of Contents
|
|
|
|
1. [Project Structure](#project-structure)
|
|
2. [Code Standards](#code-standards)
|
|
3. [Git Workflow](#git-workflow)
|
|
4. [Backend Development](#backend-development)
|
|
5. [Testing Strategy](#testing-strategy)
|
|
6. [Database Workflow](#database-workflow)
|
|
7. [Kubernetes Deployment](#kubernetes-deployment)
|
|
|
|
---
|
|
|
|
## Project Structure
|
|
|
|
We follow a strict monorepo structure managed by PNPM Workspaces.
|
|
|
|
```
|
|
Base/
|
|
├── apps/ # Frontend applications
|
|
│ ├── web-client/ # Next.js 14+ (App Router)
|
|
│ └── mobile-client/ # Flutter
|
|
├── services/ # Backend microservices
|
|
│ ├── _template/ # Template for new services
|
|
│ ├── iam-service/ # Identity & Access Management
|
|
│ └── ...
|
|
├── packages/ # Shared libraries
|
|
│ ├── logger/ # Structured logging (Winston)
|
|
│ ├── types/ # Shared DTOs & Interfaces
|
|
│ ├── http-client/ # Internal Service Client
|
|
│ └── tracing/ # OpenTelemetry configuration
|
|
├── infra/ # Infrastructure-as-Code
|
|
│ ├── traefik/ # API Gateway
|
|
│ └── databases/ # Database setup scripts
|
|
└── docs/ # Documentation (EN & VI)
|
|
```
|
|
|
|
---
|
|
|
|
## Code Standards
|
|
|
|
### Naming Conventions
|
|
|
|
* **Files**: `kebab-case.ts` (e.g., `user.controller.ts`, `app.config.ts`)
|
|
* **Classes**: `PascalCase` (e.g., `UserController`, `AuthService`)
|
|
* **Functions/Variables**: `camelCase` (e.g., `getUserById`, `isValid`)
|
|
* **Constants**: `UPPER_SNAKE_CASE` (e.g., `MAX_RETRIES`, `DEFAULT_TIMEOUT`)
|
|
* **Interfaces**: `PascalCase` (e.g., `User`, `CreateUserDto`) - *No 'I' prefix*
|
|
|
|
### Bilingual Comments
|
|
|
|
For core logic and public APIs, assume both international and Vietnamese developers reading the code.
|
|
|
|
```typescript
|
|
/**
|
|
* EN: Validates user credentials and returns a token
|
|
* VI: Xác thực thông tin người dùng và trả về token
|
|
*/
|
|
async login(dto: LoginDto): Promise<TokenResponse> { ... }
|
|
```
|
|
|
|
### TypeScript Usage
|
|
|
|
* **Strict Mode**: Enabled in `tsconfig.json`. No `any` allowed (use `unknown` if needed).
|
|
* **DTOs**: Use Zod for runtime validation and type inference.
|
|
* **Return Types**: Explicitly declare return types for all public methods.
|
|
|
|
---
|
|
|
|
## Git Workflow
|
|
|
|
### Branching Strategy
|
|
|
|
* `main`: Production-ready code.
|
|
* `develop`: Integration branch for next release.
|
|
* `feature/xyz`: New features (branch off `develop`).
|
|
* `fix/xyz`: Bug fixes (branch off `develop`).
|
|
* `hotfix/xyz`: Critical fixes (branch off `main`).
|
|
|
|
### Commit Messages
|
|
|
|
We follow [Conventional Commits](https://www.conventionalcommits.org/):
|
|
|
|
```
|
|
feat(iam): add multi-factor authentication
|
|
fix(db): correct unique constraint on email
|
|
docs(guide): update development setup
|
|
style: format code with prettier
|
|
refactor: simplify auth middleware
|
|
test: add unit tests for user service
|
|
chore: update dependencies
|
|
```
|
|
|
|
---
|
|
|
|
## Backend Development
|
|
|
|
### Creating a New API Endpoint
|
|
|
|
1. **Define DTO** (`modules/user/user.dto.ts`):
|
|
```typescript
|
|
export const CreateUserDto = z.object({
|
|
email: z.string().email(),
|
|
name: z.string().min(2),
|
|
});
|
|
export type CreateUserDto = z.infer<typeof CreateUserDto>;
|
|
```
|
|
|
|
2. **Create Service Method** (`modules/user/user.service.ts`):
|
|
* Implement business logic.
|
|
* Use `BaseRepository`.
|
|
* Throw `HttpError` (e.g., `NotFound`, `BadRequest`).
|
|
|
|
3. **Create Controller** (`modules/user/user.controller.ts`):
|
|
* Parse body with DTO: `const dto = CreateUserDto.parse(req.body)`.
|
|
* Call service.
|
|
* Return success response: `res.json({ success: true, data: result })`.
|
|
|
|
4. **Register Route** (`modules/user/index.ts`):
|
|
* Add to Express router with middlewares.
|
|
|
|
### Error Handling
|
|
|
|
Always use the custom error classes from `core/errors`:
|
|
|
|
```typescript
|
|
import { NotFoundError, ConflictError } from '../../core/errors';
|
|
|
|
if (!user) {
|
|
throw new NotFoundError('User not found');
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
## Testing Strategy
|
|
|
|
### Unit Tests (`*.test.ts`)
|
|
|
|
* **Scope**: Individual classes/functions.
|
|
* **Mocking**: Mock all external dependencies (DB, other services) using `jest-mock-extended`.
|
|
* **Location**: Co-located with source files.
|
|
* **Run**: `pnpm test`
|
|
|
|
### E2E Tests (`tests/**/*.e2e.ts`)
|
|
|
|
* **Scope**: Full API flows (Controller -> Service -> DB).
|
|
* **Database**: Use a separate test database (Dockerized).
|
|
* **Run**: `pnpm test:e2e`
|
|
|
|
### Linting & Formatting
|
|
|
|
* **Lint**: `pnpm lint` (ESLint)
|
|
* **Format**: `pnpm format` (Prettier)
|
|
* **Typecheck**: `pnpm typecheck` (TSC)
|
|
|
|
---
|
|
|
|
## Database Workflow
|
|
|
|
We use **Prisma** with **Neon PostgreSQL**.
|
|
|
|
### Migrations
|
|
|
|
1. Modify `prisma/schema.prisma`.
|
|
2. Create migration (Dev):
|
|
```bash
|
|
./scripts/db/migrate.sh iam-service dev --name add_user_profile
|
|
```
|
|
3. Apply to Production (CI/CD):
|
|
```bash
|
|
./scripts/db/migrate.sh iam-service deploy
|
|
```
|
|
|
|
### Seed Data
|
|
|
|
Populate database with initial data:
|
|
```bash
|
|
./scripts/db/seed.sh iam-service
|
|
```
|
|
|
|
### Visualizing Data
|
|
|
|
Use Prisma Studio:
|
|
```bash
|
|
pnpm --filter @goodgo/iam-service prisma studio
|
|
```
|
|
|
|
---
|
|
|
|
## Kubernetes Deployment
|
|
|
|
For local Kubernetes testing (Docker Desktop / Minikube):
|
|
|
|
```bash
|
|
# 1. Build images
|
|
docker build -t goodgo/iam-service:latest -f services/iam-service/Dockerfile .
|
|
|
|
# 2. Deploy
|
|
cd deployments/local/kubernetes
|
|
./deploy.sh
|
|
|
|
# 3. Verify
|
|
kubectl get pods -n iam-local
|
|
kubectl logs -f -l app=iam-service -n iam-local
|
|
```
|
|
|
|
See [Kubernetes Guide](./kubernetes-local.md) for detailed setup.
|