Skip to content
← Back to home

Under the hood.

For the curious and the technical: how OpenVoice turns a raw transcript into usable text, how its no-network promise is enforced rather than just stated, and where the time goes. Everything here links back to the source.

 Right Ctrl

fillerscommandsdictionarycapitalize

Real output from the formatter. This exact pair is asserted as a test in crates/ov-format/src/lib.rs.

The model hears you. The rules make it usable.

One sentence, four places to put it. Switching the target reruns the real pipeline in your browser, using the rules ported from the crate that ships in the app.

editorCode.exe

So we need to call useEffect here, then return null

sentence case · no closing period · light fillers · case transforms on · dictionaries: code

Local by default, network by exception.

Not a promise in a README that quietly stops being true the first time somebody adds a convenient dependency. A CI job fails the build.

watching00:00
Requests to a third party0
Requests to this origin0

Counted live in your browser from the Performance API, not drawn. The fonts are served from this origin, so there is no request to Google to make. If a third-party script were ever added, this counter would find it without anyone remembering to change this page.

That counter is about this website. The app is the stronger claim, and it is the one worth checking.

OpenVoice makes exactly two kinds of outbound request, and both are named in the README: a model download you asked for, and an update check you can switch off. Turning the update check off means no request is made, not that one is made with a flag attached.

Every crate that touches your microphone, transcripts, keyboard or history is sealed: no path to an HTTP client, TLS stack or socket library anywhere in its dependency graph, build scripts included. A CI job fails the build if that stops being true, so telemetry or a crash uploader cannot arrive quietly.

  • ov-coresession state machine, ports, configsealed
  • ov-formatthe formatting pipelinesealed
  • ov-audiomicrophone capturesealed
  • ov-inputkeyboard hook and text injectionsealed
  • ov-storetranscript historysealed
  • ov-asrthe speech engine supervisorsealed
  • ov-clithe headless pipelinesealed
  • ov-appthe Tauri shellno direct dependency

The shell is the weaker guarantee and it is labelled as one. Tauri links an HTTP client unconditionally, so one is present in the binary even though no OpenVoice code calls it. What CI enforces there is that no OpenVoice code reaches for the network itself: a network-capable dependency has to be added to an allow-list, and adding one means writing a decision record.

scripts/check-no-network.sh

You think faster than you type.

Most people speak around 150 words a minute and type around 40. That gap is the whole reason dictation exists.

Speaking0 words
Typing0 words

Words in one minute, at ~150 wpm spoken against ~40 wpm typed. Both figures from README, “Why”. The gap is why dictation exists; raw transcription not being writing is why almost nobody uses it.

Where the time goes.

Hotkey release to text on screen, stage by stage. Since 1.0.0 the decode starts while you are still speaking, so a long dictation lands about as fast as a short one.

Measured, stage by stage

  1. capture stopthe microphone hands back what it heard1 ms
  2. hand-offaudio reaches the decoder1 ms
  3. ASR decodeonly what was not decoded while you spoke210 ms
  4. formatpure string work1 ms
  5. injectthe target app's paste handler35 ms

Medians for dictations under three seconds, from the first 1.0.0 session on the reference machine: a small sample, stated as one. Every dictation now logs how long each stage took, and parakeet-tdt-0.6b-v2 decodes on the CPU while you speak, so the decode here is only the part you said after the last pause. Source: docs/benchmarks.

What you wait for after letting go

Dictation under 3 s
~245 ms
Dictation over 15 s
~420 ms
Over 15 s, before 1.0.0
~2.2 s

Key release to text at the caret, typical. On the reference machine: RTX 3050 Laptop (4 GB VRAM), Ryzen 5 6600H, decoding on the CPU. From README, “Measured”.

Against sending it to a server.

Only the axes that can actually be checked.

OpenVoice compared with cloud dictation services on checkable axes
AxisOpenVoiceCloud dictation
Where the audio is transcribedOn your machineOn a server
Works with no internet connectionYes, after the model downloadNo
Account requiredNoneYes
Source codePublic, Apache-2.0Varies
PriceFreeVaries
TelemetryNone, and CI fails the build if that changesNot verifiable from outside

“Cloud dictation” here means any service that transcribes on a server. No specific product is described, and every cell in that column is definitional rather than researched. Wispr Flow and superwhisper are excellent and worth paying for; the README says so too. OpenVoice exists because its author wanted something local, open, and tuned for writing code and prompting agents. If you would rather read the enforcement than the table, the CI job is thirty lines.