Skip to content

Architecture Overview

System Context

The Medipal frontend is a Nuxt 4 SPA that communicates with a REST backend, authenticates via Azure AD, and embeds questionnaire engines from a CDN. All data flows through a typed API client backed by Pinia stores.

┌──────────────────────────────────────────┐
│           Browser (mp-frontend)          │
│                                          │
│  ┌─────────────┐     ┌────────────────┐  │
│  │    Pages    │────▶│  Components    │  │
│  │  app/pages/ │     │app/components/ │  │
│  └─────────────┘     └───────┬────────┘  │
│                               │           │
│                      ┌────────▼───────┐   │
│                      │  Pinia Stores  │   │
│                      │  app/stores/   │   │
│                      └────────┬───────┘   │
│                               │           │
│                      ┌────────▼───────┐   │
│                      │   API Client   │   │
│                      │ useApi →       │   │
│                      │mp-frontend-api │   │
│                      └────────────────┘   │
└──────────────────────────────────────────┘
        │                        │
  HTTP + Bearer token       OAuth redirect
        │                        │
        ▼                        ▼
 ┌─────────────┐          ┌────────────┐
 │   Backend   │          │  Azure AD  │
 │  REST API   │          └────────────┘
 └──────┬──────┘
        │ Embed token

 ┌──────────────┐          ┌──────────┐
 │   Superset   │◀─iframe  │  Sentry  │◀─ Error events
 └──────────────┘          └──────────┘

Layer Summary

LayerPathResponsibility
Pagesapp/pages/File-based routing, layout composition, tab definitions
Componentsapp/components/Reusable UI — modals, panels, designer blocks
Storesapp/stores/Server state, mutations, business logic, modal orchestration
API Clientapp/api.config.ts + mp-frontend-apiTyped HTTP calls, token injection, 401 refresh
Composablesapp/composables/Routing, local storage, formatting helpers
Utilsapp/utils/Pure helpers, auto-imported by Nuxt
Configapp/config/Static JSON — sidebar nav, tab definitions, page labels
Pluginsapp/plugins/App bootstrap, Azure OAuth, event bus wiring

External Services

ServiceHow connectedPurpose
Backend REST APIAxios + Bearer tokenAll data CRUD, auth token exchange
Azure Active DirectoryOAuth2 redirect (/oauth/callback)SSO login
Apache Superset<iframe> embed with embed tokenAnalytics charts on Results pages
SentryJS error captureProduction error tracking
CDN<iframe src="…/engine.html">Questionnaire engine runtime (see Questionnaire Core & Engine)

Key Architectural Decisions

  • Pinia over Vuex — Composition API stores, no mutations boilerplate, better TypeScript inference.
  • iframe isolation for questionnaire engine — CSS/JS sandbox, independent deployment, framework-agnostic host support. See questionnaire engine rationale.
  • Typed API clientmp-frontend-api package is generated from the OpenAPI spec; component code never constructs raw URLs.
  • File-based routing — Nuxt derives routes from app/pages/; no manual router config needed.
  • i18n at the store leveluseI18n() is called inside stores so toast messages respect the active locale without prop drilling.