Live sermon translation into 100+ languages, running entirely on one Mac per campus: audio in, voice detection, Whisper on the GPU, NLLB-200 in its own process, and a built-in web server the congregation reads from on their phones. No audio leaves the building. This is the source only. What used to sit beside it — 14 GB of speech and translation models, 8 GB of voice bundles, 6 GB of natural voices, the Electron caches, and the app data holding the operator PIN and every service transcript — is machine state and downloaded assets, and stays in the NAS backup where it belongs. The vendored node, cloudflared and Windows ffmpeg binaries are out too (533 MB, re-fetched for packaging); the browser-side runtime beside them is kept, so a checkout still serves the congregation page. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
99 lines
4.7 KiB
Markdown
99 lines
4.7 KiB
Markdown
# Church Translate
|
||
|
||
Live sermon translation into 100+ languages. One Mac app per campus. No servers,
|
||
no deployment, no subscription.
|
||
|
||
Congregants point a phone camera at a QR code, tap their language once, and read
|
||
along — or let their phone read it aloud in their ear. No app, no account.
|
||
|
||
Built because [Kaleo](https://withkaleo.com/) is $24–149/month and
|
||
[OneAccord](https://www.oneaccord.ai/) starts at $150/month for five hours, and
|
||
both are wrappers around cloud speech and translation APIs that an M-series Mac
|
||
runs locally for nothing.
|
||
|
||
---
|
||
|
||
## How it works
|
||
|
||
Everything is inside the one app. Install it on the Mac at a campus, point it at
|
||
the pastor's microphone, and it serves the congregation page itself.
|
||
|
||
```
|
||
┌──────────────── one Mac, one campus ─────────────────┐
|
||
│ │
|
||
│ Dante ─┐ │
|
||
│ Waves ─┼─► audio in ──► voice detection │
|
||
│ M32 ───┘ │ │
|
||
│ ▼ │
|
||
│ Whisper (Mac GPU) │
|
||
│ │ │
|
||
│ NLLB-200 (separate process) │
|
||
│ │ │
|
||
│ built-in web server ──────────────┼──► phones on
|
||
│ │ the WiFi
|
||
└───────────────────────────────────────────────────────┘
|
||
```
|
||
|
||
**No audio ever leaves the Mac,** and nothing leaves the building unless you
|
||
choose to publish it. Only finished sentences cross the network, so a full
|
||
auditorium costs almost nothing to serve.
|
||
|
||
Two details that are not preference but necessity: translation runs in its own
|
||
plain-Node child process, because Chromium's allocator refuses the model's
|
||
gigabyte-sized weight blocks and kills the process; and speech recognition runs
|
||
on the GPU while translation runs on the CPU, because neither fits in the
|
||
other's runtime.
|
||
|
||
## What it costs
|
||
|
||
| | |
|
||
| --- | --- |
|
||
| Speech recognition | Whisper large-v3-turbo, on the Mac's GPU — **$0** |
|
||
| Translation, 100+ languages | NLLB-200, on the Mac's CPU — **$0** |
|
||
| Spoken audio | The listener's own phone — **$0**, at any scale |
|
||
| Serving the page | The app itself — **$0** |
|
||
| Dante input | Dante Virtual Soundcard, **~$50 once per campus** — or free via Waves or console USB |
|
||
|
||
## Performance
|
||
|
||
Measured on an M2 Max, from the end of a spoken sentence to captions on a phone.
|
||
Partial text appears well before that, so it feels quicker than the numbers.
|
||
|
||
| | |
|
||
| --- | --- |
|
||
| Live preview | updates every **500–800 ms** while the sentence is still being spoken |
|
||
| Finished sentence | **~1.6 s** behind the speaker |
|
||
| Speech recognition | 4.9× real time (accurate model) |
|
||
| Translation | ~390 ms per language, flat over 240 consecutive runs |
|
||
| Memory | plateaus at 10–11 GB; no drift across a long service |
|
||
|
||
Two speech models run at once: a fast one drives the live preview, an accurate
|
||
one produces the line the congregation keeps. They run on separate tracks, so
|
||
the preview costs the finished caption almost nothing.
|
||
|
||
## Getting started
|
||
|
||
- **[docs/SETUP.md](docs/SETUP.md)** — installing at a campus
|
||
- **[docs/AUDIO.md](docs/AUDIO.md)** — Dante, Waves SoundGrid, console USB
|
||
- **[docs/COMPANION.md](docs/COMPANION.md)** — the Stream Deck button
|
||
- **[docs/SUNDAY.md](docs/SUNDAY.md)** — print this and tape it to the desk
|
||
- **[docs/PUBLIC-ACCESS.md](docs/PUBLIC-ACCESS.md)** — optional, for people off-site
|
||
|
||
```bash
|
||
cd app && npm install && npm start # run from source
|
||
cd app && npm run dist # build the .app
|
||
```
|
||
|
||
## Things worth knowing
|
||
|
||
- **Only languages people are actually listening to get translated.** Nobody on
|
||
Icelandic means no CPU spent on Icelandic. Pin a language on the operator page
|
||
to have it ready before the first person arrives.
|
||
- **Corrections beat retraining.** Operator page → Corrections →
|
||
`have a cook => Habakkuk`. Whole-word, case-insensitive, instant.
|
||
- **A late arrival sees the last 40 lines**, so walking in halfway still makes sense.
|
||
- **Transcripts** are written per service, original and every translation, under
|
||
`~/Library/Application Support/Church Translate/data/transcripts/`.
|
||
- **Each campus is independent.** Nothing is shared, nothing syncs, and one
|
||
campus being down has no effect on another.
|