How nomutsuki/fuckingennumber works
Purpose and entry points
Number Radio is a mobile-oriented English-number listening practice app. It generates practice prompts, synthesizes a complete round as continuous MiniMax speech, and plays it reliably through browser background/lock-screen conditions. The primary UI entry is app/page.tsx; global shell and styling are app/layout.tsx and app/globals.css.
Client practice orchestration
The page collects selected number categories, round duration, voice, playback speed, and inter-number interval. It drives round lifecycle: generate prompts, request synthesized audio, display monotonic loading progress, then permit playback and manual start of a following round. Core paths: app/page.tsx, app/lib/numberGenerator.ts, app/lib/audioEngine.ts.
Number-content generation boundary
app/lib/numberGenerator.ts is the domain generator for cardinal/ordinal values, large numbers, decimals, currency, phone numbers, dates, fractions, percentages, and times. Its output is the text/content payload consumed by the TTS workflow rather than prerecorded-token composition. Historical word-token assets remain under public/audio/tokens/ but are explicitly not the production fallback path.
Audio playback and continuity
app/lib/audioEngine.ts owns browser-side audio behavior, likely including playback speed and sequencing/state handling. The architectural decision is to synthesize a whole practice round into one audio resource instead of issuing/playing isolated fragments, reducing background playback interruption risk. Relevant paths: app/lib/audioEngine.ts, app/page.tsx.
Server-side TTS service
The runtime exposes a server-side /api/tts capability implemented for a worker deployment. worker/index.ts is the request entry and boundary that keeps MINIMAX_API_KEY off the client; worker/tts.ts encapsulates MiniMax neural-TTS invocation and retry behavior. Browser code sends generated round content to this boundary and receives playable synthesized audio.
Abuse/cost control and persistence
TTS is protected by server-side rate limits: per-source hourly request/character quotas and global daily quotas, returning HTTP 429 when exhausted. The source address is retained only as a digest. The limiter and its persistence model are centered in db/rateLimit.ts and db/schema.ts; migration state is represented by drizzle/0000_overrated_terror.sql. This layer protects paid MiniMax usage, but does not replace provider-side budget monitoring.
Runtime, deployment, and build
The app uses Next.js/TypeScript for its application surface, with Node.js 22.13+ required locally. It also includes a Cloudflare Worker-style server execution path in worker/, enabling deployments that provide HTTPS, server functions/workers, environment secrets, and database-backed limiting; pure static hosting is insufficient. Deployment/build integration is configured through next.config.ts, vite.config.ts, build/sites-vite-plugin.ts, and .openai/hosting.json. The required secret contract is documented by .env.example.
Static assets
The web manifest at public/manifest.webmanifest supports installable/mobile browser behavior. public/audio/tokens/ is a substantial legacy asset corpus for mechanical word-audio assembly, retained for history rather than coupled to the current MiniMax continuous-audio pipeline.
Components 18
Browser app
- Practice page · Collects settings and runs the round lifecycle.
app/page.tsx - Number generator · Creates spoken number-content prompts across practice categories.
app/lib/numberGenerator.ts - Audio engine · Plays one synthesized round with speed and continuity handling.
app/lib/audioEngine.ts - App shell
app/layout.tsx - Global styles
app/globals.css - Web manifest
public/manifest.webmanifest
Worker TTS service
- /api/tts handler · Keeps the MiniMax secret outside browser code.
worker/index.ts - MiniMax TTS client · Invokes neural TTS and applies retries.
worker/tts.ts - MiniMax API
Rate limits
- Rate limiter · Enforces source hourly and global daily request and character quotas.
db/rateLimit.ts - Rate-limit schema · Stores source digests and quota state.
db/schema.ts - Initial migration
drizzle/0000_overrated_terror.sql
Build & deployment
- Next configuration
next.config.ts - Vite configuration
vite.config.ts - Sites Vite plugin
build/sites-vite-plugin.ts - Hosting contract · Defines hosting integration for worker-capable deployment.
.openai/hosting.json - Secret contract · Documents required deployment secrets, including the MiniMax key.
.env.example
Other components
- Legacy token audio · Historical mechanical assembly assets, not the production fallback.
Connections 16
- App shell → Practice page: renders
- Global styles → App shell: styles
- Web manifest → Practice page: supports installability
- Practice page → Number generator: generates prompts
- Practice page → /api/tts handler: sends complete round text
- /api/tts handler → Rate limiter: checks quotas
- Rate limiter → Rate-limit schema: reads and updates
- Initial migration → Rate-limit schema: creates
- /api/tts handler → MiniMax TTS client: authorizes synthesis
- MiniMax TTS client → MiniMax API: synthesizes continuous audio
- /api/tts handler → Practice page: returns playable audio
- Practice page → Audio engine: loads and controls round audio
- Vite configuration → Sites Vite plugin: uses
- Sites Vite plugin → Hosting contract: builds for
- Next configuration → Hosting contract: configures app build
- Secret contract → /api/tts handler: documents secret required by