How Meetily's VAD Filter Reduces Whisper Processing Load: A Deep Dive into the Audio Pipeline
Meetily's VAD filter strips silence and short speech fragments before they reach Whisper, reducing the audio data volume by 70-90% and dramatically lowering CPU/GPU compute requirements.
Meetily is an open-source meeting transcription tool that processes audio locally using OpenAI's Whisper model. The application implements a Voice Activity Detection (VAD) filter that acts as a pre-processor, ensuring that only meaningful speech segments are passed to the heavy-weight Whisper inference engine. This architectural decision significantly optimizes real-time transcription performance by eliminating unnecessary processing of silence and noise.
Architecture of the VAD-Whisper Pipeline
Audio Capture and Mixing
In frontend/src-tauri/src/audio/pipeline.rs, the AudioPipeline::run method captures microphone and system audio, normalizes the streams, and mixes them into a single audio stream. This mixed audio serves as the input for the VAD processing stage, occurring before any Whisper inference begins.
Continuous VAD Processing with Silero
The core VAD logic resides in frontend/src-tauri/src/audio/vad.rs within the ContinuousVadProcessor struct. According to the Meetily source code, this processor:
- Processes audio in 30 ms chunks (480 samples at 16 kHz)
- Uses the Silero VAD library for neural network-based speech detection
- Builds complete
SpeechSegmentobjects containing raw samples, timestamps, and confidence values - Applies a configurable redemption time (default 2000 ms) to bridge natural pauses, preventing single utterances from splitting into tiny fragments
Filtering Segments Before Whisper
Inside AudioPipeline::run (lines 399-410 in pipeline.rs), the pipeline implements a length-based filter to discard insignificant speech fragments:
if segment.samples.len() >= 800 { // ≥ 50 ms at 16 kHz
// send to Whisper
} else {
debug!("⏭️ Dropping short VAD segment …");
}
Segments shorter than 800 samples (50 milliseconds) are dropped immediately, while valid speech chunks are forwarded to the transcription_sender channel for Whisper processing.
Performance Impact on Whisper Processing
The VAD filter reduces the Whisper processing load through three primary mechanisms:
Silence Removal: Typical meetings contain long periods of silence between speakers. The VAD completely omits these seconds, cutting the total audio samples Whisper must decode by 70-90% depending on conversation style.
Chunk Size Reduction: Instead of feeding Whisper a continuous 48 kHz stream, the pipeline sends only speech portions resampled to 16 kHz. This reduces both data volume and the number of inference calls required.
Reduced CPU/GPU Load: Fewer inference calls translate to lower GPU memory churn and reduced CPU overhead in the Rust-side processing, resulting in faster transcription turnaround and extended battery life on laptops.
Implementation Details from the Source Code
To understand the practical implementation, examine how the pipeline processes audio segments before reaching Whisper:
// Inside AudioPipeline::run (simplified)
let speech_segments = self.vad_processor.process_audio(&mixed_audio)?;
for segment in speech_segments {
// Keep only segments ≥ 50 ms (800 samples at 16 kHz)
if segment.samples.len() >= 800 {
self.transcription_sender.send(AudioChunk {
data: segment.samples,
sample_rate: 16000,
timestamp: segment.start_timestamp_ms / 1000.0,
chunk_id: self.chunk_id_counter,
device_type: DeviceType::Microphone,
})?;
self.chunk_id_counter += 1;
}
}
You can measure the actual reduction percentage using the segment lengths:
let total_samples = mixed_audio.len();
let speech_samples: usize = speech_segments.iter()
.map(|s| s.samples.len())
.sum();
println!(
"VAD kept {:.1}% of audio ({} / {} samples)",
(speech_samples as f64 / total_samples as f64) * 100.0,
speech_samples,
total_samples
);
In typical 10-minute meeting recordings, this outputs approximately 15% of original samples surviving the VAD filter, meaning Whisper processes only a fraction of the captured audio.
Summary
- Meetily's VAD filter in
vad.rsprocesses 30 ms chunks using the Silero VAD library to detect speech segments. - The
AudioPipeline::runmethod inpipeline.rsfilters out segments shorter than 800 samples (50 ms) before sending audio to Whisper. - By removing silence and bridging natural pauses with a 2000 ms redemption time, the system reduces audio data volume by 70-90%.
- This pre-filtering significantly decreases CPU/GPU load, memory churn, and battery consumption while maintaining transcription accuracy.
Frequently Asked Questions
What is the minimum speech duration that Meetily's VAD filter accepts?
Meetily discards any speech segments shorter than 800 samples, which equates to 50 milliseconds at the 16 kHz sample rate. This threshold is hardcoded in the AudioPipeline::run method within pipeline.rs to prevent Whisper from processing meaningless audio fragments.
Which VAD library does Meetily use?
The application uses the Silero VAD library, implemented through the ContinuousVadProcessor struct in frontend/src-tauri/src/audio/vad.rs. This library provides pre-trained neural network models optimized for detecting human speech in noisy environments with minimal latency.
How does the redemption time setting affect transcription?
The redemption time (configured at 2000 ms by default) determines how long the VAD waits after detecting speech ends before finalizing a segment. This bridges natural pauses in speech, preventing a single sentence from being split into multiple tiny fragments that would otherwise be filtered out or processed separately by Whisper.
Can the VAD filter be disabled to process all audio?
While the source code shows the VAD is tightly integrated into AudioPipeline::run, modifying the pipeline to bypass the process_audio call and remove the length check would send all audio to Whisper. However, this would eliminate the performance benefits and significantly increase resource consumption, making real-time transcription impractical on most hardware.
Have a question about this repo?
These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:
curl -s "https://instagit.com/install.md" Maintain an open-source project? Get it listed too →