Files
InvestPlay/docs/DEVELOPMENT-ROADMAP.md
Lefteris Notas e75f913f1c
Some checks failed
CI / Lint (push) Has been cancelled
CI / TypeCheck (push) Has been cancelled
CI / Test (push) Has been cancelled
Deploy / Docker Build & Push (map[context:. dockerfile:apps/api/Dockerfile name:api]) (push) Has been cancelled
Deploy / Docker Build & Push (map[context:. dockerfile:apps/cms/Dockerfile name:cms]) (push) Has been cancelled
Deploy / Docker Build & Push (map[context:. dockerfile:apps/web/Dockerfile name:web]) (push) Has been cancelled
CI / Build (push) Has been cancelled
Deploy / Deploy (push) Has been cancelled
feat: complete Phase 1 foundation scaffold
- Monorepo: Turborepo + pnpm workspaces with 7 apps/packages
- Backend: NestJS scaffold with 9 modules (auth, tenant, curriculum, simulation, portfolio, ai-coach, analytics, classroom, gamification)
- Frontend: React 18 + Vite + TailwindCSS + shadcn/ui with 10 pages, 14 UI primitives, 3 Zustand stores
- Database: Prisma schema with 19 models, 13 enums, seed script, multi-tenant ready
- Docker: Dev, production, and Portainer Compose files with Traefik reverse proxy
- Configuration: .env.example (47 vars), Zod validation, frontend-safe env exposure
- i18n: English + Greek locale files (10 files), ICU MessageFormat, react-i18next
- Shared packages: @investplay/types, @investplay/ui, @investplay/i18n, @investplay/utils
- CI/CD: GitHub Actions (lint, typecheck, test, build, deploy, PR checks)
- Documentation: CONTEXT.md, ARCHITECTURE.md (10 Mermaid diagrams), API.md, LOCALIZATION.md, DEVELOPMENT-ROADMAP.md
- Infrastructure: Dockerfiles (dev + prod), nginx configs, backup/healthcheck scripts
- Security: JWT auth guards, role-based access, rate limiting, Helmet, CORS, PII sanitization
2026-06-12 19:32:57 +03:00

14 KiB

InvestPlay — Development Roadmap

Status: Phase 1 — Foundation
Last Updated: 2026-06-12
Target: Production-grade, multi-tenant, multi-platform financial literacy platform


Architecture Decisions

Decision Choice Rationale
Monorepo Tool Turborepo Better DX than Nx for this scale; native ESM support
Package Manager pnpm Disk-efficient, strict dependency resolution
Backend Framework NestJS Modular, DI, GraphQL native, WebSocket integrated
Frontend Framework React + Vite Fast HMR, modern tooling, Capacitor/Tauri compatible
CMS Payload CMS (self-hosted) Code-first, TypeScript-native, block-based content, i18n built-in
Database ORM Prisma Type-safe, migration-first, multi-schema for tenant isolation
Cache Redis BullMQ queues + session store + rate limiting
Auth Clerk (initial) → Auth0 (B2B SSO) Fast B2C start, SAML SSO for institutions
i18n Framework next-intl / react-i18next ICU message format, locale-aware routing
CSS Framework TailwindCSS + shadcn/ui Design tokens, accessible components
Containerization Docker Compose (dev) + Portainer (prod) Consistent local/remote, easy management
CI/CD GitHub Actions Free for public repos, Docker layer caching

Development Phases

PHASE 1 — Foundation COMPLETED (2026-06-12)

Goal: Running monorepo, Docker dev environment, auth, basic API, empty UI shell

  • Project documentation and roadmap
  • Monorepo structure (Turborepo + pnpm workspaces)
  • Docker Compose for local dev (PostgreSQL, Redis, MinIO, Payload CMS)
  • Docker Compose for Contabo/Portainer production deployment
  • Environment variable system (.env per service, validation via Zod)
  • NestJS backend scaffold with core modules (75 files, 9 modules)
  • Prisma schema — 19 models, 13 enums, users, tenants, roles, classrooms
  • Auth module (JWT + SSO ready)
  • Tenant module (multi-tenancy, feature flags)
  • React + Vite frontend scaffold (55+ files, 10 pages, 14 UI primitives)
  • TailwindCSS + shadcn/ui design system
  • i18n infrastructure (EN + EL, 10 locale files, ICU MessageFormat)
  • Shared packages: @investplay/types, @investplay/ui, @investplay/i18n, @investplay/utils
  • Payload CMS scaffold with Docker support
  • ESLint + Prettier + Husky pre-commit hooks
  • CI pipeline (lint, typecheck, test, build) + deploy + PR checks
  • Comprehensive documentation (CONTEXT.md, ARCHITECTURE.md, API.md, LOCALIZATION.md)

PHASE 2 — Core Learning (MVP B2C)

Goal: Self-guided learner can complete lessons and earn XP

  • CMS block renderer in frontend (Hero, Text, Quiz, Calculator blocks)
  • Lesson progression engine (track → module → lesson → block)
  • XP and leveling system
  • Badges and achievements
  • Quiz/assessment engine
  • User dashboard with progress visualization
  • Streak tracking
  • B2C auth flow (email + social)

PHASE 3 — Simulations & Gamification

Goal: Interactive simulations and mini-games work end-to-end

  • Blind Scenario engine (historical CSV → WebSocket tick stream)
  • Synthetic market generator
  • Portfolio management (virtual trades, ROI calculation)
  • Budget Game (50/30/20 drag-and-drop)
  • Debt Snowball mini-game
  • Hype Trap narrative challenge
  • Anti-cheat mechanisms
  • Simulation leaderboards

PHASE 4 — AI Coach

Goal: Context-aware educational AI with cost controls

  • AI proxy service (NestJS → OpenAI/Gemini)
  • Context injection pipeline
  • Token bucket rate limiting (per user, per tenant)
  • BYOK (Bring Your Own Key) mode
  • Socratic prompt engineering
  • Audit logging
  • PII sanitization before LLM calls
  • Graceful fallback when quota exhausted

PHASE 5 — Classroom & Institutions (B2B MVP)

Goal: Teachers can manage classrooms and institutions can deploy

  • Teacher dashboard
  • Classroom creation with invite codes
  • Assignment system
  • Live "Time Machine" classroom simulation
  • Cohort analytics and heatmaps
  • Intervention alerts
  • PDF/CSV report generation
  • Institution admin panel
  • White-label configuration
  • Stripe Connect B2B billing
  • SSO integration (SAML/OIDC)

PHASE 6 — Mobile & Desktop

Goal: Native app wrappers for iOS, Android, Windows, macOS, Linux

  • Capacitor wrapper (iOS + Android)
  • Push notifications (FCM)
  • Offline lesson caching
  • Tauri v2 wrapper (Windows, macOS, Linux)
  • Desktop-specific features (offline mode, system tray)

PHASE 7 — Analytics & Reporting

Goal: Data-driven insights for institutions and platform operators

  • Behavioral telemetry pipeline
  • Aggregated materialized views (nightly rollups)
  • Teacher analytics dashboard
  • PDF/CSV automated report generation
  • GDPR anonymization pipeline
  • Opt-out mechanism for research aggregation
  • "Gen Z Financial Behavior Index" report templates

PHASE 8 — Localization Expansion

Goal: Full EU language support

  • Add DE, FR, ES, IT, PT, NL locales
  • CMS content localization workflow
  • Locale-specific financial examples (taxes, regulations)
  • RTL support readiness
  • Locale-aware currency and number formatting

PHASE 9 — Production Hardening

Goal: Enterprise-grade security, performance, and reliability

  • Load testing (k6 / Artillery)
  • Penetration testing
  • Database backup/restore automation
  • Disaster recovery plan
  • Multi-region deployment (EU data residency)
  • SOC 2 / ISO 27001 readiness
  • SLA monitoring and alerting

i18n Strategy

Implementation

  • UI Strings: react-i18next with ICU MessageFormat in JSON files per locale
  • Educational Content: Payload CMS localized collections (each lesson has locale variants)
  • Currency/Number Formatting: Intl.NumberFormat (browser-native, no extra library)
  • Date Formatting: Intl.DateTimeFormat with locale-aware relative time

Locale File Structure

packages/i18n/src/locales/
  en/
    common.json        # Buttons, nav, errors
    finance.json       # Financial terms, instrument names
    gamification.json  # XP, badges, achievement names
    classroom.json     # Teacher dashboard, assignments
    ai-coach.json      # AI chat UI strings
  gr/
    common.json
    finance.json
    ...

Initial Languages (Phase 1)

  • English (en) — Primary development language
  • Greek (el) — Market entry requirement

Expansion Languages (Phase 8)

  • German (de), French (fr), Spanish (es), Italian (it), Portuguese (pt), Dutch (nl)
  • All EU official languages eventually

Deployment Architecture

Local Development (Windows)

docker compose -f docker-compose.dev.yml up

Services:

  • api — NestJS backend (hot-reload via tsx watch)
  • web — Vite React frontend (HMR on port 5173)
  • cms — Payload CMS (port 3000)
  • postgres — PostgreSQL 16 (port 5432)
  • redis — Redis 7 (port 6379)
  • minio — S3-compatible storage (ports 9000/9001)

Contabo Production (via Portainer)

docker compose -f docker-compose.prod.yml up -d

Portainer stack deployment with:

  • Traefik reverse proxy (auto-SSL via Let's Encrypt)
  • Multi-stage Docker builds (CI → GHCR → Portainer pull)
  • Health checks on all containers
  • Log rotation via Docker logging drivers
  • Database backup sidecar container

Environment Variables

All configuration through environment variables. No hardcoded secrets.

Required ENV Files

.env.example              # Template for all vars (committed)
.env                      # Local overrides (gitignored)
.env.production.example   # Production template (committed)

Key Variable Categories

Category Variables
Database DATABASE_URL, DATABASE_POOL_MIN, DATABASE_POOL_MAX
Redis REDIS_URL, REDIS_PASSWORD
Auth JWT_SECRET, JWT_EXPIRES_IN, CLERK_SECRET_KEY
AI OPENAI_API_KEY, GEMINI_API_KEY, AI_DEFAULT_DAILY_LIMIT
Storage S3_ENDPOINT, S3_ACCESS_KEY, S3_SECRET_KEY, S3_BUCKET
Email RESEND_API_KEY, EMAIL_FROM
Billing STRIPE_SECRET_KEY, STRIPE_WEBHOOK_SECRET
Tenant TENANT_DEFAULT_AI_MODE, TENANT_MAX_TOKENS_MONTHLY
i18n DEFAULT_LOCALE, SUPPORTED_LOCALES

Repository Structure

investplay/
├── apps/
│   ├── api/                    # NestJS backend
│   │   ├── src/
│   │   │   ├── modules/
│   │   │   │   ├── auth/
│   │   │   │   ├── tenant/
│   │   │   │   ├── curriculum/
│   │   │   │   ├── simulation/
│   │   │   │   ├── portfolio/
│   │   │   │   ├── ai-coach/
│   │   │   │   ├── analytics/
│   │   │   │   ├── classroom/
│   │   │   │   └── gamification/
│   │   │   ├── common/
│   │   │   │   ├── guards/
│   │   │   │   ├── decorators/
│   │   │   │   ├── filters/
│   │   │   │   └── interceptors/
│   │   │   ├── config/
│   │   │   └── main.ts
│   │   ├── prisma/
│   │   │   ├── schema.prisma
│   │   │   └── migrations/
│   │   ├── test/
│   │   ├── Dockerfile
│   │   └── package.json
│   ├── web/                    # React + Vite frontend
│   │   ├── src/
│   │   │   ├── components/
│   │   │   ├── pages/
│   │   │   ├── hooks/
│   │   │   ├── stores/
│   │   │   ├── lib/
│   │   │   ├── styles/
│   │   │   └── i18n/
│   │   ├── public/
│   │   ├── index.html
│   │   ├── vite.config.ts
│   │   ├── Dockerfile
│   │   └── package.json
│   ├── cms/                    # Payload CMS
│   │   ├── src/
│   │   │   └── collections/
│   │   ├── package.json
│   │   └── Dockerfile
│   ├── mobile/                 # Capacitor wrapper
│   └── desktop/                # Tauri v2 wrapper
├── packages/
│   ├── types/                  # @investplay/types
│   │   ├── src/
│   │   │   ├── user.ts
│   │   │   ├── tenant.ts
│   │   │   ├── curriculum.ts
│   │   │   ├── simulation.ts
│   │   │   ├── portfolio.ts
│   │   │   └── analytics.ts
│   │   └── package.json
│   ├── ui/                     # @investplay/ui
│   │   ├── src/
│   │   │   ├── components/
│   │   │   └── lib/
│   │   └── package.json
│   ├── i18n/                   # @investplay/i18n
│   │   ├── src/
│   │   │   └── locales/
│   │   └── package.json
│   └── utils/                  # @investplay/utils
│       ├── src/
│       └── package.json
├── docker/
│   ├── docker-compose.dev.yml
│   ├── docker-compose.prod.yml
│   ├── traefik/
│   │   ├── traefik.yml
│   │   └── dynamic.yml
│   └── nginx/
│       └── nginx.conf
├── scripts/
│   ├── setup.sh
│   ├── seed.ts
│   └── backup.sh
├── docs/
│   ├── DEVELOPMENT-ROADMAP.md
│   ├── CONTEXT.md
│   ├── API.md
│   └── ARCHITECTURE.md
├── .github/
│   └── workflows/
│       ├── ci.yml
│       └── deploy.yml
├── .env.example
├── .env.production.example
├── turbo.json
├── pnpm-workspace.yaml
├── package.json
├── tsconfig.base.json
├── .eslintrc.js
├── .prettierrc
└── README.md

Database Schema (Core Entities)

User                — id, email, role, locale, tenantId, xp, level
Tenant              — id, name, domain, branding, featureFlags, aiMode
Classroom           — id, name, tenantId, teacherId, inviteCode
ClassroomStudent    — id, classroomId, userId, joinedAt
Module              — id, cmsId, track, order, tenantId
Lesson              — id, cmsId, moduleId, order, estimatedMins
UserProgress        — id, userId, lessonId, status, score, completedAt
QuizAttempt         — id, userId, quizId, answers, score, timestamp
Trade               — id, userId, simulationId, asset, amount, timestamp
Portfolio           — id, userId, simulationId, cashBalance, holdings
Badge               — id, name, description, icon, criteria
UserBadge           — id, userId, badgeId, earnedAt
AILog               — id, tenantId, userId, tokensUsed, timestamp
AnalyticsEvent      — id, userId, eventType, metadata, timestamp

Key Technical Decisions

Multi-Tenancy Strategy

Schema-level isolation via PostgreSQL schemas (one per tenant) for maximum data isolation. Tenant-specific connection pooling via Prisma's multi-schema preview feature.

API Design

  • Primary: GraphQL for all CRUD operations (type-safe, no over-fetching)
  • Real-time: WebSockets (Socket.io) for live simulations and leaderboards
  • Webhooks: REST endpoints for Stripe, Resend, third-party integrations

AI Cost Control

Backend-side hard enforcement (not reliant on OpenAI budget alerts):

  • Redis token bucket per user (daily) and per tenant (monthly)
  • Hard cutoff at quota exhaustion (no grace period)
  • Admin alert when approaching 80% of monthly quota

Security

  • JWT with RS256 (asymmetric) for service-to-service auth
  • GraphQL query depth limiting (max depth 7)
  • Rate limiting on all public endpoints
  • CORS whitelist per tenant domain
  • Helmet.js for HTTP security headers
  • Input validation via Zod on every endpoint
  • Prompt injection defense in AI proxy

Tracking

Progress tracked via this file. Each completed task gets [x].
Git commits follow Conventional Commits format. CI badges added once pipelines are running.