# EDR Platform - Ethio-Djibouti Railway Passenger API Enterprise-grade NestJS REST API for the Ethio-Djibouti Railway passenger booking and management platform. Built with TypeScript, PostgreSQL, and Prisma ORM. ## ๐Ÿš€ Features ### ๐Ÿ†• NEW: Age-Based Pricing, Verifayda 2.0 & Multi-Currency #### Age-Based Pricing - **ADULT** (โ‰ฅ5 years): Pay 100% of base fare - **CHILD** (<5 years): First child travels FREE, subsequent children pay 100% - Automatic age calculation from date of birth - Example: 2 adults + 3 children = 4ร— base fare (first child free) #### Verifayda 2.0 Integration - Real-time Ethiopian national ID verification - Retrieves passenger data from government database - National IDs NOT stored (policy compliant) - Non-Ethiopians use passport (no verification required) - Booking fails if verification unsuccessful #### Multi-Currency Support - **Transaction Currency**: ETB (Ethiopian Birr) - **Display Currencies**: ETB, DJF (Djiboutian Franc), USD (US Dollar) - Real-time exchange rate conversion - Prices shown in user's preferred currency - Exchange rates: ETBโ†’DJF=3.25, ETBโ†’USD=0.018 ### Core Modules - **Authentication & Authorization** - Dual authentication system: - **Passenger Auth**: JWT-based auth with OTP verification, password reset, account lockout - **Corporate IAM**: Integration with @tria-plc corporate identity system for back-office operations (agents, supervisors, admins) - Role-based access control (RBAC) with granular permissions - **Age-Based Pricing** - Smart passenger categorization: - **ADULT** (โ‰ฅ5 years): Full fare - **CHILD** (<5 years): First child free, subsequent children full fare - Automatic age calculation from date of birth - **Verifayda 2.0 Integration** - Ethiopian national ID verification: - Real-time verification via government API - Retrieves passenger data (name, DOB, nationality) - National IDs NOT stored (policy compliant) - Non-Ethiopians use passport (no verification) - **Multi-Currency Support** - Display prices in multiple currencies: - **ETB** (Ethiopian Birr) - Transaction currency - **DJF** (Djiboutian Franc) - Display option - **USD** (US Dollar) - Display option - Real-time exchange rate conversion - **Booking Management** - Complete booking lifecycle: - **Guest Booking**: Book without login, optional account creation - **Saved Passengers**: Store passenger details for quick rebooking - Modification, cancellation, refunds, and fare breakdown - Multi-segment journey support - **Payment Integration** - Multi-provider support (Telebirr, CBE Birr, eBirr, Card, Wallet) with webhook handling - **Seat Management** - Real-time seat inventory: - Seat holds with 5-minute expiry - Seat releases and blocking with coach/class management - Segment-based seat availability (partial journey bookings) - Auto-assign seats with contiguous algorithm - CSV import/export for seat configurations - **Ticketing** - QR code and barcode generation, PDF tickets, gate validation with audit logs - **Agent Operations** - Counter booking, shift management, commission tracking, and reconciliation - **Passenger Services** - Profile management, traveler profiles, saved routes, and preferences - **Loyalty Program** - Points accumulation, tier management (Bronze/Silver/Gold/Platinum), and rewards - **Wallet System** - Balance management, top-up, transaction ledger - **Live Tracking** - Real-time trip status, location updates, delay notifications, crowd signals - **Notifications** - Multi-channel (Email, SMS, Push) with templating engine - **Support System** - FAQ management, live chat conversations - **Reports & Analytics** - Revenue reports, occupancy analytics, agent sales tracking - **Route Management** - Route configuration, stops, fare rules, baggage allowance ### Technical Features - **Security** - Password hashing (bcrypt), JWT tokens, rate limiting, audit logging - **Validation** - Request validation with class-validator, DTO transformation - **Documentation** - Auto-generated Swagger/OpenAPI docs at `/api-docs` - **Error Handling** - Global exception filters with standardized error responses - **Database** - PostgreSQL with Prisma ORM, migrations, and comprehensive seeding - **Scheduling** - Cron jobs for automated tasks (seat release, report generation) - **Event System** - Event-driven architecture with @nestjs/event-emitter ## ๐Ÿ“‹ Prerequisites - **Node.js** >= 20.x - **pnpm** >= 9.x (`npm install -g pnpm`) - **PostgreSQL** >= 15.x - **Git** ## ๐Ÿ› ๏ธ Installation & Setup ### 1. Clone Repository ```bash git clone cd edr-platform ``` ### 2. Install Dependencies ```bash pnpm install ``` ### 3. Environment Configuration ```bash # Copy environment template cp apps/edr-passenger-api/.env.example apps/edr-passenger-api/.env # Edit .env file with your configuration ``` #### Required Environment Variables | Variable | Description | Example | |----------|-------------|---------| | `NODE_ENV` | Environment mode | `development` | | `PORT` | HTTP server port | `4000` | | `DATABASE_URL` | PostgreSQL connection string | `postgresql://user:pass@localhost:5432/edr_passenger` | | `JWT_SECRET` | JWT signing secret (change in production) | `your-secret-key` | | `JWT_EXPIRES_IN` | JWT token expiry | `7d` | | `PORTAL_URL` | Web app CORS origin | `http://localhost:3000` | | `BACK_OFFICE_URL` | Admin portal CORS origin | `http://localhost:3001` | | `SENDGRID_API_KEY` | SendGrid API key (optional) | `SG.xxx` | | `SENDGRID_FROM_EMAIL` | Email sender address | `noreply@edr-platform.com` | #### Verifayda 2.0 Configuration (Ethiopian National ID Verification) | Variable | Description | Example | |----------|-------------|---------| | `VERIFAYDA_ENABLED` | Enable Verifayda integration | `true` or `false` | | `VERIFAYDA_API_URL` | Verifayda API endpoint | `https://api.verifayda.gov.et/v2` | | `VERIFAYDA_API_KEY` | API key for Verifayda service | `your-verifayda-api-key` | **Note:** When `VERIFAYDA_ENABLED=false`, verification is skipped (development mode only). #### Corporate IAM Configuration (Back-office Authentication) | Variable | Description | Example | |----------|-------------|---------| | `IAM_ENABLED` | Enable corporate IAM integration | `true` or `false` | | `IAM_API_URL` | Corporate IAM API endpoint | `https://iam.tria-plc.com/api` | | `IAM_API_KEY` | API key for IAM service | `your-iam-api-key` | **Note:** When `IAM_ENABLED=false`, IAM-protected routes allow access without validation (development mode only). #### Optional: Payment Provider Configuration ```bash # Telebirr Configuration TELEBIRR_BASE_URL=https://api.telebirr.com TELEBIRR_MERCHANT_CODE=your-merchant-code TELEBIRR_APP_SECRET=your-app-secret # ... see .env.example for complete list ``` ### 4. Database Setup #### Start PostgreSQL ```bash # Using Docker (recommended) docker run --name edr-postgres \ -e POSTGRES_USER=edr \ -e POSTGRES_PASSWORD=edr_secret \ -e POSTGRES_DB=edr_passenger \ -p 5432:5432 \ -d postgres:15 # Or use your local PostgreSQL installation ``` #### Generate Prisma Client ```bash pnpm --filter @edr/passenger-api run prisma:generate ``` #### Run Migrations ```bash pnpm --filter @edr/passenger-api run prisma:migrate:dev ``` #### Seed Database ```bash pnpm --filter @edr/passenger-api run prisma:seed ``` **Seed Data Includes:** - 21 Stations (Complete Ethiopian-Djibouti Railway with country codes) - 1 Route with 21 stops and fare rules - 2 Train services with 4 trips - 360 seats across 12 coaches (Economy Regular, Economy Bed, VIP Bed classes) - 3 User accounts (Admin, Passenger, Agent) - Fare rules for ADULT and CHILD passenger categories - Currency exchange rates (ETB, DJF, USD) - Baggage allowance rules - Notification templates - Promotions and FAQ content - Menu items and station crowd signals - Fraud detection rules - Saved passenger profiles for testing ### 5. Start Development Server ```bash pnpm --filter @edr/passenger-api run dev ``` **API Server:** http://localhost:4000 **Swagger Docs:** http://localhost:4000/api-docs ## ๐Ÿ”‘ Default Credentials After seeding, use these credentials to test the API: | Role | Email | Password | Description | |------|-------|----------|-------------| | **Admin** | `admin@edr-platform.com` | `admin123` | Full system access, reports, agent management | | **Passenger** | `kelemu@email.com` | `password123` | Regular user with loyalty (Silver) and wallet | | **Agent** | `agent@edr-platform.com` | `agent123` | Counter booking agent with commission tracking | ## ๐Ÿ“š API Documentation ### Swagger UI Interactive API documentation available at: **http://localhost:4000/api-docs** ### Authentication Methods The API uses two authentication schemes: #### 1. JWT Authentication (Passenger-facing) - **Used for**: Passenger bookings, profile management, wallet, loyalty - **Header**: `Authorization: Bearer ` - **Obtain token**: `POST /auth/login` with passenger credentials - **Swagger Security**: `JWT-auth` #### 2. IAM Authentication (Back-office) - **Used for**: Agent operations, fraud detection, reports, admin functions - **Header**: `Authorization: Bearer ` - **Obtain token**: From corporate IAM system (https://iam.tria-plc.com) - **Swagger Security**: `IAM-auth` - **Roles**: AGENT, SUPERVISOR, ADMIN, STAFF ### API Endpoints Overview | Module | Base Path | Auth Type | Description | |--------|-----------|-----------|-------------| | **Auth** | `/auth` | Public/JWT | Register, login, OTP verification, password reset | | **Passengers** | `/passengers` | Public/JWT | Verifayda verification, international registration, profiles | | **Search** | `/search` | Public | Trip search, availability, fare quotes | | **Stations** | `/stations` | Public/JWT | Station directory and information | | **Seats** | `/seats` | JWT/IAM | Seat maps, holds, releases, blocking | | **Bookings** | `/bookings` | Public/JWT | Guest booking, create, modify, cancel bookings | | **Payments** | `/payments` | JWT/Public | Payment initiation, webhooks, refunds | | **Tickets** | `/tickets` | JWT/IAM | Ticket generation, QR/barcode, validation | | **Notifications** | `/notifications` | JWT | In-app notifications, preferences | | **Loyalty** | `/loyalty` | JWT | Points, tiers, rewards redemption | | **Wallet** | `/wallet` | JWT | Balance, top-up, transaction history | | **Promotions** | `/promos` | Public/JWT | Active promotions, promo code validation | | **Live Tracking** | `/live` | Public/JWT | Real-time trip status, crowd signals | | **Support** | `/support` | Public/JWT | FAQ, chat conversations | | **Dashboard** | `/dashboard` | JWT | Home screen aggregated data | | **Routes** | `/routes` | JWT/IAM | Reusable route templates with ordered stops | | **Schedules** | `/schedules` | JWT/IAM | Trip schedules, fare rules, status updates | | **Fleet** | `/fleet` | JWT/IAM | Train services, coaches, seat configurations | | **Seat Classes** | `/seat-classes` | Public/JWT/IAM | Seat class management and configuration | | **Segment Seats** | `/segments/seats` | Public/JWT | Segment-based seat availability and booking | | **Agents** | `/agents` | IAM | Agent booking, shifts, commissions, reconciliation | | **Fraud Detection** | `/fraud` | IAM | Fraud alerts, rules management, user blocking | | **Reports** | `/reports` | IAM | Revenue, occupancy, agent sales analytics | ### Example API Calls #### 1. Register Passenger ```bash POST /auth/register Content-Type: application/json { "email": "user@example.com", "phone": "+251911234567", "fullName": "John Doe", "password": "SecurePass123" } ``` #### 2. Login (Passenger) ```bash POST /auth/login Content-Type: application/json { "email": "user@example.com", "password": "SecurePass123" } # Response includes JWT token { "accessToken": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...", "user": { "id": "uuid", "role": "PASSENGER" } } ``` #### 3. Verify Ethiopian National ID (Verifayda) ```bash POST /passengers/verify-fayda Content-Type: application/json { "nationalId": "ET123456789" } # Response with verified passenger data { "verified": true, "passengerData": { "fullName": "Abebe Kebede", "dateOfBirth": "1985-03-15T00:00:00.000Z", "gender": "Male", "nationality": "Ethiopian" } } ``` #### 4. Register International Passenger ```bash POST /passengers/register-international Content-Type: application/json { "passengerName": "John Smith", "dateOfBirth": "1990-07-20", "passportNumber": "P1234567", "passportCountry": "Kenya", "nationality": "Kenyan", "phone": "+254712345678", "email": "john@example.com" } ``` #### 5. Search Trips ```bash POST /search Content-Type: application/json { "originStationId": "uuid", "destinationStationId": "uuid", "date": "2026-06-15", "adultCount": 2, "childCount": 1 } ``` #### 6. Get Fare Quote ```bash POST /search/fare-quote Content-Type: application/json { "tripId": "uuid", "serviceClass": "ECONOMY_REGULAR", "adultCount": 2, "childCount": 1, "displayCurrency": "USD" } # Response includes age-based pricing breakdown { "baseFareMinor": 35000, "adultCount": 2, "adultFareMinor": 70000, "childCount": 1, "freeChildrenCount": 1, "paidChildrenCount": 0, "childFareMinor": 0, "totalMinor": 73500, "currency": "ETB", "displayCurrency": "USD", "displayTotalMinor": 1323 } ``` #### 7. Guest Booking (No Login Required) ```bash POST /bookings/guest Content-Type: application/json { "tripId": "uuid", "holdId": "uuid", "serviceClass": "ECONOMY_REGULAR", "displayCurrency": "ETB", "passengers": [ { "seatId": "uuid", "passengerName": "Abebe Kebede", "dateOfBirth": "1985-03-15", "idDocumentType": "NATIONAL_ID", "idDocumentNumber": "ET123456789" } ], "createAccount": false, "savePassengerDetails": true, "deviceId": "device-uuid" } ``` #### 8. Agent Booking (IAM Auth) ```bash POST /agents/bookings Authorization: Bearer Content-Type: application/json { "tripId": "uuid", "seats": [...], "paymentMethod": "CASH", "cashReceived": 50000 } ``` ## ๐Ÿ—๏ธ Project Structure ``` apps/edr-passenger-api/ โ”œโ”€โ”€ prisma/ โ”‚ โ”œโ”€โ”€ schema.prisma # Database schema (40+ models) โ”‚ โ”œโ”€โ”€ seed.ts # Comprehensive seed script โ”‚ โ””โ”€โ”€ migrations/ # Database migrations โ”œโ”€โ”€ src/ โ”‚ โ”œโ”€โ”€ common/ # Shared utilities โ”‚ โ”‚ โ”œโ”€โ”€ filters/ # Exception filters โ”‚ โ”‚ โ”œโ”€โ”€ interceptors/ # Response interceptors โ”‚ โ”‚ โ”œโ”€โ”€ pipes/ # Validation pipes โ”‚ โ”‚ โ”œโ”€โ”€ i18n/ # Internationalization โ”‚ โ”‚ โ”œโ”€โ”€ jwt.guard.ts # JWT authentication guard (passengers) โ”‚ โ”‚ โ”œโ”€โ”€ jwt.strategy.ts # Passport JWT strategy โ”‚ โ”‚ โ”œโ”€โ”€ iam-adapter.ts # Corporate IAM guard (back-office) โ”‚ โ”‚ โ”œโ”€โ”€ iam.module.ts # IAM module โ”‚ โ”‚ โ”œโ”€โ”€ roles.guard.ts # RBAC authorization guard โ”‚ โ”‚ โ”œโ”€โ”€ roles.decorator.ts # Roles decorator โ”‚ โ”‚ โ”œโ”€โ”€ prisma.service.ts # Prisma client service โ”‚ โ”‚ โ””โ”€โ”€ prisma.module.ts # Prisma module โ”‚ โ”œโ”€โ”€ config/ # Configuration files โ”‚ โ”‚ โ”œโ”€โ”€ app.config.ts # App configuration โ”‚ โ”‚ โ”œโ”€โ”€ database.config.ts # Database configuration โ”‚ โ”‚ โ””โ”€โ”€ telebirr.config.ts # Payment provider config โ”‚ โ”œโ”€โ”€ modules/ # Feature modules โ”‚ โ”‚ โ”œโ”€โ”€ auth/ # Authentication & authorization (JWT) โ”‚ โ”‚ โ”œโ”€โ”€ agents/ # Agent operations (IAM-protected) โ”‚ โ”‚ โ”œโ”€โ”€ bookings/ # Booking management (JWT) โ”‚ โ”‚ โ”œโ”€โ”€ currency/ # Currency conversion service โ”‚ โ”‚ โ”œโ”€โ”€ dashboard/ # Dashboard aggregations (JWT) โ”‚ โ”‚ โ”œโ”€โ”€ fleet/ # Train fleet management (JWT/IAM) โ”‚ โ”‚ โ”œโ”€โ”€ fraud/ # Fraud detection (IAM-protected) โ”‚ โ”‚ โ”œโ”€โ”€ live/ # Live tracking (JWT) โ”‚ โ”‚ โ”œโ”€โ”€ loyalty/ # Loyalty program (JWT) โ”‚ โ”‚ โ”œโ”€โ”€ notifications/ # Notification system (JWT) โ”‚ โ”‚ โ”œโ”€โ”€ passengers/ # Passenger management (JWT) โ”‚ โ”‚ โ”œโ”€โ”€ payments/ # Payment processing (JWT/Webhooks) โ”‚ โ”‚ โ”œโ”€โ”€ promos/ # Promotions (JWT) โ”‚ โ”‚ โ”œโ”€โ”€ reports/ # Reports & analytics (IAM-protected) โ”‚ โ”‚ โ”œโ”€โ”€ schedules/ # Trip schedules (JWT/IAM) โ”‚ โ”‚ โ”œโ”€โ”€ search/ # Trip search (JWT) โ”‚ โ”‚ โ”œโ”€โ”€ seats/ # Seat management (JWT/IAM) โ”‚ โ”‚ โ”œโ”€โ”€ segments/ # Journey segments (JWT) โ”‚ โ”‚ โ”œโ”€โ”€ stations/ # Station management (JWT) โ”‚ โ”‚ โ”œโ”€โ”€ support/ # Customer support (JWT) โ”‚ โ”‚ โ”œโ”€โ”€ tickets/ # Ticketing (JWT/IAM) โ”‚ โ”‚ โ”œโ”€โ”€ verifayda/ # Verifayda 2.0 integration โ”‚ โ”‚ โ””โ”€โ”€ wallet/ # Wallet system (JWT) โ”‚ โ”œโ”€โ”€ app.module.ts # Root application module โ”‚ โ””โ”€โ”€ main.ts # Application entry point โ”œโ”€โ”€ test/ # E2E tests โ”œโ”€โ”€ .env.example # Environment template โ”œโ”€โ”€ Dockerfile # Docker configuration โ”œโ”€โ”€ nest-cli.json # NestJS CLI configuration โ”œโ”€โ”€ package.json # Dependencies & scripts โ”œโ”€โ”€ tsconfig.json # TypeScript configuration โ””โ”€โ”€ tsconfig.build.json # Build configuration ``` ## ๐Ÿ—„๏ธ Database Schema ### Key Models (40+ total) **Core Entities:** - `User`, `Session`, `Passenger`, `Agent` - `Station`, `Route`, `RouteStop`, `RouteFareRule` - `TrainService`, `Trip`, `TripStopTime`, `Coach`, `Seat` - `Booking`, `BookingSeat`, `Ticket` - `PaymentIntent`, `PaymentRefund`, `PaymentWebhookEvent` **Enhanced Features:** - `OtpCode`, `PasswordResetToken` (Auth) - `AgentBooking`, `AgentShift`, `AgentCommission` (Agents) - `BookingModification`, `BookingCancellation` (Booking lifecycle) - `GateValidationLog` (Ticket validation) - `BaggageAllowance`, `BaggageBooking` (Baggage) - `LoyaltyAccount`, `LoyaltyLedgerEntry`, `LoyaltyReward` - `WalletAccount`, `WalletLedgerEntry` - `Notification`, `NotificationTemplate` - `AuditLog`, `OperationalReport` - `SeatBlock`, `SeatHold` - `CurrencyExchangeRate` (Multi-currency) - `VerifaydaVerification` (National ID verification) - `SavedPassengerProfile` (Guest booking) - `SeatClass` (Seat class configuration) - `JourneySegment` (Multi-segment journeys) ## ๐Ÿ”ง Available Scripts ```bash # Development pnpm --filter @edr/passenger-api run dev # Start with hot-reload # Build pnpm --filter @edr/passenger-api run build # Compile TypeScript # Production pnpm --filter @edr/passenger-api run start # Run compiled code # Testing pnpm --filter @edr/passenger-api run test # Unit tests pnpm --filter @edr/passenger-api run test:e2e # E2E tests # Code Quality pnpm --filter @edr/passenger-api run lint # ESLint pnpm --filter @edr/passenger-api run type-check # TypeScript check # Database pnpm --filter @edr/passenger-api run prisma:generate # Generate Prisma client pnpm --filter @edr/passenger-api run prisma:migrate:dev # Run migrations (local dev) pnpm --filter @edr/passenger-api run prisma:seed # Seed database ``` ## ๐Ÿณ Docker Deployment All six apps build from Dockerfiles: each API has its own (`apps/edr-freight-api/Dockerfile`, `apps/edr-passenger-api/Dockerfile`); Vite frontends share `infrastructure/docker/Dockerfile.web` and are served with **nginx**. APIs run on **Node 22**. **Prerequisites** - Docker with BuildKit enabled - A local [`.npmrc`](.gitignore) with GitHub Packages auth for `@tria-plc/*` (required for **freight** API and web images) - External Postgres for each API (compose does **not** include databases) - Copy `apps/edr-freight-api/.env.example` โ†’ `.env` and `apps/edr-passenger-api/.env.example` โ†’ `.env` with real connection strings ### Build and run (all apps) ```bash # From monorepo root DOCKER_BUILDKIT=1 pnpm docker:build pnpm docker:up ``` Or without pnpm scripts: ```bash DOCKER_BUILDKIT=1 docker compose build docker compose up -d ``` | Service | URL (default) | |---------|----------------| | Freight API | http://localhost:3001 | | Passenger API | http://localhost:4000 | | Freight portal | http://localhost:5173 | | Freight backoffice | http://localhost:5183 | | Passenger portal | http://localhost:5174 | | Passenger backoffice | http://localhost:5184 | ### Build a single service ```bash docker compose build freight-api docker compose build passenger-portal ``` Freight images mount `.npmrc` as a BuildKit secret during `pnpm install`. Passenger web images do not require private packages. ### `VITE_API_URL` (frontends) API URLs are **baked in at image build time** (`import.meta.env.VITE_API_URL`). Defaults in [`docker-compose.yaml`](docker-compose.yaml) use `http://localhost:3001/api` (freight) and `http://localhost:4000` (passenger) for local smoke tests. Override build args for production, e.g.: ```bash docker compose build freight-portal \ --build-arg VITE_API_URL=https://freight-api.example.com/api ``` ### Migrations - **Freight API:** TypeORM migrations are not run on container startup โ€” apply them separately before deploy. - **Passenger API:** On each container start, the entrypoint runs `npm run prisma:migrate` and `npm run prisma:seed` (same `package.json` scripts as `pnpm run`) before starting the server. Ensure `DATABASE_URL` in `.env` points at a reachable Postgres instance. For local development, use `pnpm --filter @edr/passenger-api run prisma:migrate:dev` instead of `prisma:migrate`. ### GitHub Actions (self-hosted runner) Two workflows deploy independently on push to `main`, `develop`, or `staging`: | Workflow | Services | Server env root | |----------|----------|-----------------| | [`.github/workflows/deploy-freight.yml`](.github/workflows/deploy-freight.yml) | freight-api, freight-portal, freight-backoffice | `/home/user/environmen/edr-freight//` | | [`.github/workflows/deploy-passenger.yml`](.github/workflows/deploy-passenger.yml) | passenger-api, passenger-portal, passenger-backoffice | `/home/user/environmen/edr-passenger//` | **On the runner**, place env files before the first deploy (example for branch `main`): ```text /home/user/environmen/edr-freight/main/ freight-api.env freight-portal.env # optional runtime env for Vite/nginx freight-backoffice.env freight-web.build.env # exports FREIGHT_VITE_API_URL=... /home/user/environmen/edr-passenger/main/ passenger-api.env passenger-portal.env passenger-backoffice.env passenger-web.build.env # exports PASSENGER_VITE_API_URL=... ``` Example `freight-web.build.env`: ```bash export FREIGHT_VITE_API_URL=https://freight-api.example.com/api ``` The workflow copies `*.env` into each app directory, creates `.npmrc` from the `NPM_TOKEN` repository secret, then runs `docker compose build` and `docker compose up -d` for that stack. ## ๐Ÿ”’ Security Best Practices 1. **Environment Variables** - Never commit `.env` files. Use secrets management in production. 2. **JWT Secret** - Use strong, randomly generated secrets (min 32 characters). 3. **Password Hashing** - Bcrypt with salt rounds (default: 10). 4. **Rate Limiting** - Implement rate limiting for auth endpoints. 5. **CORS** - Configure allowed origins in production. 6. **HTTPS** - Always use HTTPS in production. 7. **Database** - Use connection pooling and prepared statements (Prisma handles this). 8. **Audit Logging** - All sensitive operations are logged in `AuditLog` table. 9. **Dual Authentication** - Passenger routes use JWT, back-office routes use corporate IAM. 10. **IAM Integration** - Corporate IAM validates tokens against centralized identity service. 11. **Role-Based Access** - Granular permissions enforced via IAM roles (AGENT, SUPERVISOR, ADMIN). 12. **Token Validation** - IAM tokens validated in real-time with 5-second timeout. ## ๐Ÿ“Š Monitoring & Logging - **Application Logs** - NestJS built-in logger - **Database Queries** - Prisma query logging (enable in development) - **Audit Trail** - All user actions logged in `AuditLog` table - **Error Tracking** - Global exception filters with detailed error responses ## ๐Ÿงช Testing ```bash # Unit tests pnpm --filter @edr/passenger-api run test # E2E tests pnpm --filter @edr/passenger-api run test:e2e # Test coverage pnpm --filter @edr/passenger-api run test:cov ``` ## ๐Ÿš€ Production Deployment ### Pre-deployment Checklist - [ ] Update environment variables (JWT_SECRET, DATABASE_URL, etc.) - [ ] Configure IAM integration (IAM_ENABLED=true, IAM_API_URL, IAM_API_KEY) - [ ] Configure Verifayda integration (VERIFAYDA_ENABLED=true, VERIFAYDA_API_KEY) - [ ] Set up currency exchange rate sync (external API) - [ ] Set NODE_ENV=production - [ ] Configure CORS origins (PORTAL_URL, BACK_OFFICE_URL) - [ ] Set up SSL/TLS certificates - [ ] Configure database connection pooling - [ ] Set up monitoring and logging - [ ] Configure backup strategy - [ ] Test payment provider integrations - [ ] Verify IAM token validation endpoint - [ ] Test Verifayda verification with real national IDs - [ ] Verify currency conversion accuracy - [ ] Test age-based pricing calculations - [ ] Review security settings and audit logs - [ ] Test both JWT and IAM authentication flows ### Deployment Steps ```bash # 1. Build application pnpm --filter @edr/passenger-api run build # 2. Run migrations pnpm --filter @edr/passenger-api run prisma:migrate # 3. Start production server NODE_ENV=production pnpm --filter @edr/passenger-api run start:prod ``` ## ๐Ÿค Contributing 1. Fork the repository 2. Create feature branch (`git checkout -b feature/amazing-feature`) 3. Commit changes (`git commit -m 'Add amazing feature'`) 4. Push to branch (`git push origin feature/amazing-feature`) 5. Open Pull Request ## ๐Ÿ“ License This project is proprietary and confidential. ## ๐Ÿ“ง Support For technical support or questions: - Email: support@edr-platform.com - Documentation: http://localhost:4000/api-docs --- **Built with โค๏ธ for Ethio-Djibouti Railway**