Back to AI/ML Overview
⌨️ Production Consumer Product

CosmicKeysMulti-Region Typing Platform, Voice-Narrated, AI-Personalized

A live consumer typing platform with voice narration, 7-language localization across 9 regions, anycast traffic routing across US/Europe/Asia, real-time WebSocket analytics, and AI-generated personalized lessons. Built as a solo developer in under 8 months.

7 langs
localized content
9 regions
deployed coverage
3 continents
anycast routing
<100ms
real-time keystroke feedback
WebSocket
analytics pipeline
Live
cosmickeys.app

πŸ”What Most Visitors Don't See

When people visit cosmickeys.app, they see a beautiful typing practice platform with animated finger guides. What they don't see is the production architecture underneath: a multi-region traffic cop routing requests across three continents, a voice narration pipeline that generates audio lessons in seven languages, a real-time WebSocket layer tracking every keystroke, and an AI personalization loop that adapts lessons to each learner's progress.

πŸ”‘The polish that isn't visible is where the engineering lives
Anyone can ship a typing app in a weekend with Next.js. Shipping a typing app that handles users in Tokyo, Frankfurt, and San Francisco with sub-100ms keystroke feedback, voice narration in the user's native language, automatic region failover, and AI-driven curriculum adaptation β€” that's the interesting part. Most of this work is invisible to end users, which is exactly how it's supposed to be.

πŸ—οΈSystem Overview

CosmicKeys Global Architecture
Users Worldwide7 languages, 9 regionsAnycast Traffic Copedge routing β€” lowest latency wins, health-check failoverUS RegionprimaryNext.js + FastAPIEU RegionreplicaNext.js + FastAPIAsia RegionreplicaNext.js + FastAPIprivate backbone Β· cross-region replicationPostgreSQLprimary + regional replicaswrites via primary, reads localWebSocket Gatewaylive keystroke pipelineper-user session stateAI Personalization PipelineClaude β€” adaptive lesson selectionprogress-driven curriculum tuningNext.js + FastAPI + PostgreSQL + WebSocket Β· Docker deployed across 3 regions
🌐

Edge Layer

Anycast traffic cop routes each request to the geographically nearest region. Users in Tokyo hit Asia, users in Frankfurt hit EU, users in California hit US β€” all transparent, all automatic.

⚑

Compute Layer

Next.js frontend + FastAPI backend deployed in each region. Shared services (auth, content, analytics) run on private backbone with cross-region replication.

πŸ’Ύ

Data Layer

PostgreSQL with a primary write node and regional read replicas. WebSocket gateway streams keystroke events into a time-series pipeline feeding the personalization loop.

πŸ›°οΈThe Traffic Cop: Multi-Region Anycast Routing

This is the part most engineers wave off with β€œjust put it behind Cloudflare.” That works until you have stateful services, database write consistency, and region-specific localization. I designed a deliberate routing strategy that handles all three.

Three Problems the Traffic Cop Solves

1. Latency: Route to the nearest region

For a real-time typing platform, every 50ms of round-trip latency is user-visible. Anycast routing at the edge sends each user to the geographically nearest data center. A user in Tokyo hits Asia; a user in London hits Europe; a user in Seattle hits US-West. Zero configuration, automatic.

2. Failover: Survive a region going down

Health checks run continuously against each region's FastAPI health endpoint. When a region fails or degrades, the traffic cop withdraws it from the anycast pool and traffic automatically spills over to the next-closest healthy region. Users see a brief reconnect on WebSocket but the experience stays alive.

3. Localization: Serve region-appropriate content

Each region serves localized content β€” Japanese in Asia, German and French in EU, English variants in US. The traffic cop attaches a region header that the backend uses for content selection. The localization is cache-friendly: each region's CDN caches its own language variants, not a global cache invalidated by any single update.

🌍7 Languages Γ— 9 Regions Localization

Localization is usually treated as an afterthought β€” a post-launch β€œinternationalization” project. I designed it as a first-class architectural concern from day one because retrofitting i18n into a typing platform (where literally every character on the screen has to localize) is a nightmare.

The Languages

EnglishSpanishFrenchGermanJapaneseKoreanChinese

Localization Scope β€” Beyond UI Strings

πŸ”€

Character Sets

Latin, CJK (Chinese-Japanese-Korean), and Cyrillic handling β€” each requires distinct rendering, input method editor (IME) support, and keyboard layout logic.

⌨️

Keyboard Layouts

QWERTY, QWERTZ, AZERTY, Dvorak β€” plus language-specific layouts for non-Latin scripts. Finger animation guides must match the user's actual keyboard.

πŸ“–

Lesson Content

Typing exercises, sample sentences, and progressive difficulty curves are all localized. Beginner lessons in Japanese use hiragana progressions, not the same lessons as English.

πŸ—£οΈ

Voice Narration

Every instructional prompt has a native-speaker audio variant. The user hears lesson guidance in their language, not English subtitles.

πŸ“

Units and Formatting

Words-per-minute vs characters-per-minute (critical for CJK where "word" is ambiguous). Dates, numbers, and comparisons formatted per locale.

🎨

Cultural Theming

Color palettes and imagery adapted where colors carry cultural meaning. Error states don't use red in cultures where red signals success.

πŸŽ™οΈVoice Narration Pipeline

One of the features that gets zero credit from first-time visitors is the voice narration system. Every instructional prompt β€” β€œplace your left index finger on F, your right index on J” β€” has a professionally-generated audio variant in every supported language.

Voice Generation Pipeline
Lesson Content
source material, English
canonical instructional prompts
Localization Translation
LLM-assisted + human review
produces per-language text variants
TTS Pipeline
per-locale voice model
native-speaker audio for each language
Audio Assets
CDN-cached per region
stored close to listeners, not at origin
Lazy-loaded at Lesson Start
downloaded on demand
minimal bandwidth for the 99% of lessons a user never opens
πŸ’‘Why the audio is per-region, not per-user
Each region caches its own audio variants, so a user in Tokyo downloads Japanese audio from the Asia CDN, not from a US origin halfway around the world. This is one of the invisible wins: the user hears instant voice feedback because the audio was already cached 50ms away from them, not 200ms away.

πŸ“‘Real-Time WebSocket Analytics

Every keystroke a user makes flows into a WebSocket pipeline in real time. This isn't for vanity metrics β€” it's the data layer that powers adaptive difficulty, personalized curriculum, and the progress dashboards users see live during their sessions.

What Gets Streamed

⌨️

Keystroke Events

Character pressed, timing delta, accuracy flag. The foundation of everything else.

⏱️

Words Per Minute

Rolling average over the last N keystrokes, streamed to the UI so users see live progress.

🎯

Error Patterns

Which keys the user mistypes most often β€” used to adapt lesson difficulty in real time.

πŸ”₯

Session Heatmaps

Finger-level accuracy heatmap feeding the visual feedback layer (glow intensity per finger).

πŸ“ˆ

Progress Milestones

Lesson completions, new speed records, streak achievements β€” dispatched to the notification layer.

🧠

Feature Vectors

Aggregated metrics feed into the AI personalization pipeline for next-lesson selection.

πŸ”‘Why WebSocket and not REST polling
Typing is latency-sensitive. If feedback lags by 200ms, the rhythm breaks and users feel disconnected from the keyboard. REST polling would introduce this kind of lag. Persistent WebSockets let the server push updates the instant they're ready β€” the user sees their WPM tick up character by character.

🧠AI Personalization Loop

This is the feature that turns CosmicKeys from a typing game into a learning platform. After each lesson, the user's performance flows into an AI decision loop that adapts the next lesson to their weaknesses.

Personalization Decision Loop
Lesson Result
WPM, accuracy, error pattern
streamed live from the WebSocket layer at lesson completion
Aggregate with Historical Data
last N lessons, skill progression
builds a feature vector describing the learner's current state
LLM Decision Step
Claude β€” "what next?"
scores candidate lessons from the curriculum pool against the learner's gaps
Personalized Next Lesson
localized + voice-narrated
difficulty tuned to the user's current level, served to the UI

The LLM receives the user's recent performance, the curriculum pool, and the user's declared goals, and returns a ranked list of next-best lessons. The system picks the top choice and serves it β€” localized, narrated, with difficulty tuned to the user's current level.

πŸ›‘οΈFailover and Resilience

What happens when a region goes down? The short answer: users don't notice. The long answer requires careful design at every layer.

❀️

Continuous Health Checks

Each region exposes a /health endpoint. The traffic cop polls every few seconds and pulls failing regions out of the anycast pool within seconds.

πŸ”„

Automatic Spillover

When a region fails, users in that region are routed to the next-closest healthy region. Keystroke streams reconnect over WebSocket within 1-2 seconds.

πŸ“‹

Write Consistency

Writes go to a primary database region; reads can be served from any replica. During failover, writes are delayed briefly rather than split-brained.

πŸ’Ύ

Local Session Cache

The client keeps a local cache of the current lesson so that a brief connection loss does not interrupt the user's typing session.

πŸ”§The Tech Stack

Frontend

  • β€’ Next.js 15 (App Router) + React 19
  • β€’ TypeScript strict mode
  • β€’ Tailwind CSS v4 for styling
  • β€’ Framer Motion for animations
  • β€’ WebSocket client for real-time analytics

Backend

  • β€’ FastAPI (Python 3.14) for REST endpoints
  • β€’ FastAPI WebSocket for live analytics
  • β€’ SQLAlchemy ORM + async Postgres driver
  • β€’ Anthropic SDK for personalization LLM calls
  • β€’ Pydantic for request/response validation

Data

  • β€’ PostgreSQL primary + regional read replicas
  • β€’ Redis for session cache and WebSocket pub/sub
  • β€’ CDN cache for localized audio assets per region

Infrastructure

  • β€’ Multi-region deployment (US / EU / Asia)
  • β€’ Anycast DNS at the edge for traffic routing
  • β€’ Health-check-based failover
  • β€’ Docker containerized services
🎯

Leadership Takeaway

The uncomfortable truth about β€œfully global” consumer products: most startups claim to be global on day one but ship single-region, English-only software with a translation dropdown bolted on three months later. Truly global β€” voice-narrated per locale, latency-optimized per region, keyboard-layout-aware per market β€” is a different engineering problem.

What this demonstrates: I can take a consumer product from zero to multi-region production with localization as a first-class concern, not an afterthought. That's the difference between β€œtechnically international” and β€œactually usable by a user in Tokyo who speaks no English.”

How this would scale inside a company: every architectural component here β€” the traffic cop, the localization pipeline, the voice generation, the WebSocket analytics, the AI personalization β€” is a reusable pattern that could be pulled into a platform team to serve many product teams. Multi-region consumer infrastructure is expensive to build once and cheap to replicate. I've done it solo as a proof; the same pattern scales to teams.