Skip to content
LedgeurLedgeur
Speaker diarization

Working out who said what, without the audio leaving your machine.

Diarization is the part of transcription that turns a wall of text into a record you can act on. Almost every product that does it does it in a cloud. Ledgeur does it in your browser, with two open models and about two hundred lines of arithmetic.

Pricing before the conference
Today · 3 speakers
Recording 04:12
Priya

The only thing I want to settle today is whether we ship the pricing change before or after the conference.

Speaker 271%

Before. If we wait we spend the whole conference explaining a price nobody can buy yet.

Priya

Then we need the billing migration done by Thursday. Sam, can you own that?

Sam

I can, but I want the rollback path reviewed first. I'll have something to look at tomorrow morning.

Action items
  • Sam — billing migration, with a reviewed rollback path, by Thursday
  • Ship the pricing change before the conference
An illustration of the app. Your own transcript is whatever your meeting says — Ledgeur never invents a word of it.
The pipeline

Three stages, two models, no upload.

Both models are ONNX, both run through WebGPU where there is one and the CPU where there is not, and both are cached after the first run so it works with the wifi off.

Segmentationpyannote/segmentation-3.0

Where does the voice change?

Handles up to three people talking at once, which matters because overlap is where naive approaches produce a transcript that attributes half a sentence to the wrong person.

EmbeddingWeSpeaker VoxCeleb ResNet34-LM

What does this stretch of speech sound like, as a vector?

A 256-number fingerprint of a voice. Comparing two of them answers whether two stretches of audio are the same person, without either of them being labelled.

ClusteringPure TypeScript, in packages/core/src/diarize

Which of these vectors are the same person?

The deciding is not a model at all, which is why it is unit-tested without a browser and shared by the live and imported paths. It runs once over the whole meeting, because 'is this the same person' cannot be answered twenty seconds at a time.

What separation alone does not give you

Speaker 2 is useful exactly once.

Diarization tells you there were four people. It does not tell you which one was Priya, and a transcript full of Speaker 3 is a transcript nobody searches.

So Ledgeur keeps the voice print. Rename Speaker 2 to Priya once, and her fingerprint is saved under that name. Next Tuesday she speaks, the print matches, and the transcript says Priya before you have read a line of it. Each meeting refines the print as a running average, so one bad headset does not undo ten good recordings.

Voice prints live in your browser’s own storage and are never synced, not even on the paid plan. A voice print identifies a person after the transcript has been deleted, which makes it the most sensitive thing the product holds, so it stays where it was made. That is asserted by a test, not just by this paragraph.

Naming, without guessing

Meetings usually say who is in them.

Somebody introduces themselves, or answers to their name. When a recording finishes, the on-device model reads the transcript and names the voices it can prove.

There is deliberately no pattern-matching here. A regular expression pulling “I’m X” out of a transcript cannot tell “I’m Max” from “I’m afraid not”, and a wrong name propagates into every later meeting through the voice store. So the model proposes and a validator throws out anything it cannot check.

  • The name has to actually be spoken in the transcript.
  • The quoted evidence has to be a real line, and the line that says the name.
  • It has to clear a belief threshold: 0.75 to put a label on, 0.85 to teach the voice.
  • One name per voice, one voice per name.

Every name that survives is shown as a guess, with the belief and the words it came from, everywhere it appears. Correcting one also un-teaches whatever it taught the voice store, so a wrong name cannot quietly become the truth.

pyannote segmentation 3.0WeSpeaker ResNet34Runs on your deviceMIT source

How this compares

 LedgeurA hosted notetaker
Where diarization runsYour browserThe vendor's servers
Where the voice print livesYour device, never syncedTheir account, if it exists at all
Cost per hour of audioYour CPUMetered minutes
Whether you can checkMIT source, open the network tabA privacy policy

Read nextHow Whisper runs in a browser tab

Try it on a recording you already have

Drag in a voice memo, a Zoom export, an old interview. It is treated exactly like a live meeting, and nothing is uploaded.