Architecture IWEY API
Modular NestJS monolith (ESM) + multi-schema PostgreSQL + dynamic RBAC.
Ports & HTTP surfaces
| Surface | URL (port PORT, default 3000) |
Access |
|---|---|---|
| Home | http://localhost:{PORT}/ |
Public |
| REST API | http://localhost:{PORT}/api/* |
JWT Bearer (except @Public routes) |
| Swagger UI | http://localhost:{PORT}/docs |
Public (enabled in development) |
| Architecture (this doc) | http://localhost:{PORT}/architecture |
Public |
| Academic concepts | http://localhost:{PORT}/academic-concepts |
Public |
| Architecture JSON | http://localhost:{PORT}/architecture.json |
Public |
| Messaging realtime guide | http://localhost:{PORT}/messaging-realtime |
Public |
| Socket.IO messaging | namespace /messaging (same host/port) |
JWT at handshake |
| Health (TCP) | :{PORT} |
Docker healthcheck |
Error message language: Accept-Language, ?lang=fr|en, or x-lang header.
Layers
src/
├── main.ts # bootstrap, ValidationPipe, Swagger, api prefix
├── app.module.ts # composition + APP_GUARD (JWT, Permissions)
├── shared/ # cross-cutting (guards, decorators, i18n, filters)
├── infrastructure/ # TypeORM persistence (9 Postgres schemas)
├── modules/ # business domains
│ ├── auth/ # JWT auth / sessions
│ ├── permissions/ # catalog + RBAC matrix
│ ├── profile/ # profile + settings
│ ├── dashboard/ # admin/director stats
│ ├── pedagogy/ # courses, virtual-classes, lessons…
│ ├── evaluation/ # homeworks, practical works, attendance, grades
│ ├── communication/ # messages, announcements, work groups
│ └── kora/ # files
└── tenants/ # multi-tenant (license)
Domains ↔ SQL schemas
| Nest module | Postgres schema (DDL) | Responsibility |
|---|---|---|
| auth + profile | identity |
Accounts, sessions, profiles, RBAC |
| pedagogy | pedagogy |
Courses, sections, virtual classes |
| evaluation | evaluation |
Homeworks, practical works, attendance, grades |
| communication | communication |
Messaging, announcements |
| kora | kora |
File storage |
| tenants / platform | platform |
License, logs |
| (structure) | academic_structure |
Institution, programs… |
| (tuition) | tuition |
Fees, enrollments |
| (docs) | academic_documents |
Academic records / documents |
Note: Postgres schema/table/column names are English in the DDL. TypeORM entity folders/classes match and map via
@Entity({ schema, name })/@Column({ name })when needed.
Security
- JWT access + refresh (revocable sessions; in-memory for now).
- Deny-by-default permissions (
@RequirePermissions, OR). - Role × permission matrix aligned with frontend (
docs/rbac-inconsistencies.md). - Scope
self/own/all: planned, scope guard to wire. - DTO validation (
class-validator) + whitelist.
i18n
- Locales:
src/shared/i18n/locales/{fr,en}/messages.json - Exceptions:
I18nHttpException/ helpersi18nUnauthorized,i18nNotFound, … - HTTP filter translates
messageKey→ localized message +langfield
Code conventions
- Imports via
@/only (no relatives). - Files ≤ 300 lines.
- Single-statement
if→ no braces. - GWT tests in English, one assertion, mocks in unit tests.
- Folders, entity class/file names, and Nest modules in English.
Exposed business modules (Swagger tags)
Auth · Profile · Settings · Dashboard · Courses · VirtualClasses · Homeworks · PracticalWorks · Attendance · Grades · Announcements · Messages · WorkGroups · Users · Resources
Realtime messaging
Socket.IO namespace /messaging (private + group chats). Full client guide: docs/messaging-realtime.md — also served at /messaging-realtime.
Security
See docs/security-backend.md and Cursor rule .cursor/rules/backend-security.mdc (agent-requestable).
Deployment
- Dev:
docker compose -f docker-compose.dev.yml up --build - Prod:
docker compose -f docker-compose.prod.yml --env-file .env.production up -d --build - DDL init:
database/01_schema.sql(+database/02_seed.sqlon first boot in dev)