Operations

Decisions & Changelog

The reasoning behind the big choices, and a running log of what we've shipped.

Key decisions

Realtime layer

Self-hosted LiveKit

Open-source WebRTC SFU we fully control; keeps healthcare media on our own infra and avoids per-minute SaaS pricing.

Provisioning

Pulumi (TypeScript)

Infrastructure as real code in the same language as the app, with typed config and a proper module system for sharing logic across clouds.

DNS

Cloudflare (unproxied)

A neutral DNS authority decoupled from any cloud. Proxying is off so WebRTC's UDP/TURN paths aren't broken.

Server bootstrap

cloud-init + Docker Compose

First-boot configuration with no manual steps, so any VM rebuild is reproducible and identical.

Shared core

Provider-neutral modules

LiveKit + cloud-init logic lives in infra/shared and is imported verbatim by every cloud stack — the heart of portability.

Documentation

React Router 7 app

This wiki is a real app (Tailwind + shadcn/ui) that will evolve into the simulation client and admin portal.

Changelog

Iteration 1Web
  • Scaffolded the React Router 7 app (Tailwind v4 + shadcn/ui) as a living architecture wiki and future client.
Iteration 1Fix
  • Diagnosed a ~15s browser reconnect loop; upgraded LiveKit server v1.8.0 → v1.12.0 (data-tracks protocol compatibility).
Iteration 1GCP
  • Deployed the identical stack to Google Cloud reusing the shared modules.
  • Verified parity: valid TLS, healthy endpoint, 0% packet-loss media.
Iteration 1Azure
  • Stood up the first self-hosted LiveKit deployment on an Azure VM.
  • Moved DNS to Cloudflare and automated TLS via Caddy + Let's Encrypt.