# How Meetily Implements Import Audio for Subsequent Re-Transcription

> Discover how Meetily implements import audio, treating files as new meetings. Re-transcribe recordings later using different languages, models, or providers. Learn the process.

- Repository: [Zackriya Solutions/meetily](https://github.com/Zackriya-Solutions/meetily)
- Tags: how-to-guide
- Published: 2026-07-18

---

**Meetily treats imported audio files as new meetings by copying them into a local directory and processing them through the same decode-resample-VAD-transcription pipeline used for live recordings, enabling users to re-transcribe them later with different languages, models, or providers.**

Meetily is an open-source meeting transcription application from Zackriya-Solutions that unifies external audio files and live recordings under a single processing architecture. The **import audio feature for subsequent re-transcription** allows users to ingest existing audio files, store them persistently, and re-process them multiple times using various transcription engines without re-importing the source file.

## Import Pipeline Architecture

When a user imports an audio file, Meetily creates a dedicated meeting folder and runs the audio through a standardized pipeline that ensures compatibility with both Whisper and Parakeet transcription engines.

### File Selection and Validation

The process begins with a Tauri command that opens a native file dialog and validates the selected file. In [`frontend/src-tauri/src/audio/import.rs`](https://github.com/Zackriya-Solutions/meetily/blob/main/frontend/src-tauri/src/audio/import.rs), the `select_and_validate_audio_command` function (lines 21‑44) handles the initial user interaction, checking file extensions and returning basic file information to the frontend before any processing begins.

### Background Processing and Pipeline

Once validation succeeds, `start_import_audio_command` (lines 71‑80) spawns the import job in a background async task. The system acquires an `ImportGuard` to set the global `IMPORT_IN_PROGRESS` flag (lines 62‑64), preventing concurrent import operations and ensuring thread safety.

The pipeline executes the following stages sequentially:

1. **Meeting folder creation**: `create_meeting_folder` generates a new directory under the default recordings path (lines 42‑44)
2. **Audio copying**: The source file is copied into the meeting folder as `audio.<ext>` (typically `mp4`), preserving the original (lines 48‑63)
3. **Decoding**: `decode_audio_file_with_progress` runs on a blocking thread to convert container formats into raw PCM (lines 73‑81)
4. **Resampling**: `to_whisper_format_with_progress` converts audio to 16 kHz mono format, the standard required by Whisper models (lines 104‑110)
5. **Voice Activity Detection**: `get_speech_chunks_with_progress` applies VAD with a 2000 ms redemption time—longer than the live pipeline—to identify speech segments accurately (lines 122‑130)

### Metadata Creation

After successful processing, Meetily writes a [`metadata.json`](https://github.com/Zackriya-Solutions/meetily/blob/main/metadata.json) file using `write_import_metadata` (lines 78‑104). This implementation uses atomic file operations: it writes to a temporary file first, then renames it to ensure consistency even if the process terminates unexpectedly. The metadata includes a `"source":"import"` tag, meeting ID, duration, and audio filename.

Finally, `unload_engine_after_batch` (lines 80‑82) releases the transcription engine to free system resources, regardless of whether the job succeeded, failed, or was cancelled.

## Re-Transcription Implementation

Re-transcription leverages the same core utilities as the initial import, ensuring consistent audio processing while allowing flexible transcription parameters.

### Locating Stored Audio

When a re-transcription request arrives, `find_audio_file` in [`frontend/src-tauri/src/audio/retranscription.rs`](https://github.com/Zackriya-Solutions/meetily/blob/main/frontend/src-tauri/src/audio/retranscription.rs) (lines 39‑66) searches the meeting folder for standard audio filenames or any file matching supported extensions. This locates the previously imported audio without requiring the user to re-select the file.

### Re-running the Processing Stages

The `run_retranscription` function (lines 100‑220 and 236‑400) executes the identical pipeline used during import: decode → resample → VAD → optional segment-splitting → transcription. However, unlike the fixed settings used during initial import, re-transcription accepts parameters for `language`, `model`, and `provider`, allowing users to switch between Whisper and Parakeet engines or select different model sizes without re-importing the audio.

Progress events are emitted at each stage, enabling the frontend to display real-time status updates through the `retranscription-progress` event channel.

### Updating Metadata

Upon completion, `write_retranscription_metadata` (lines 723‑756) updates [`metadata.json`](https://github.com/Zackriya-Solutions/meetily/blob/main/metadata.json) with `"source":"retranscription"` and records a `retranscribed_at` timestamp. The system writes new transcripts to [`transcripts.json`](https://github.com/Zackriya-Solutions/meetily/blob/main/transcripts.json) via `audio::common` utilities, then emits a `retranscription-complete` event containing the meeting ID, segment count, duration, and language used (lines 14‑24).

## Implementation Details

### Shared Utilities and Consistency

Both import and re-transcription modules rely on `audio::decoder`, `audio::vad`, and `audio::common` as defined in [`src/audio/mod.rs`](https://github.com/Zackriya-Solutions/meetily/blob/main/src/audio/mod.rs). This shared architecture ensures identical VAD parameters (such as `VAD_REDEMPTION_TIME_MS = 2000`) and segment-splitting logic apply whether processing live recordings, imported files, or re-transcription jobs.

### Cancellation and Concurrency Protection

Meetily implements global atomic flags including `IMPORT_IN_PROGRESS`, `IMPORT_CANCELLED`, `RETRANSCRIPTION_IN_PROGRESS`, and `RETRANSCRIPTION_CANCELLED` to prevent overlapping jobs and enable graceful aborts. The `ImportGuard` and equivalent re-transcription guards automatically clear these flags when the processing scope ends.

### Provider Flexibility

The pipelines accept an optional `provider` parameter that defaults to Whisper but switches to Parakeet when `"parakeet"` is specified. Boolean checks like `use_parakeet` in both [`import.rs`](https://github.com/Zackriya-Solutions/meetily/blob/main/import.rs) and [`retranscription.rs`](https://github.com/Zackriya-Solutions/meetily/blob/main/retranscription.rs) determine which transcription engine handles the audio segments.

## Code Examples

### Importing Audio via Frontend

```typescript
import { invoke } from '@tauri-apps/api/tauri';

// Open file dialog, validate, then start import
const fileInfo = await invoke('select_and_validate_audio_command');
if (fileInfo) {
  await invoke('start_import_audio_command', {
    source_path: fileInfo.path,
    title: 'Team Sync',
    language: 'en',
    model: undefined,          // use default model
    provider: undefined      // use Whisper
  });
}

```

### Listening for Import Progress

```typescript
import { listen } from '@tauri-apps/api/event';

listen('import-progress', e => {
  console.log('Import progress:', e.payload);
});

listen('import-complete', e => {
  console.log('Import finished – meeting ID:', e.payload.meeting_id);
});

```

### Triggering Re-Transcription

```typescript
await invoke('start_retranscription_command', {
  meeting_id: '<meeting‑id>',
  meeting_folder_path: '/Users/me/Library/Application Support/Meetily/recordings/Team Sync',
  language: 'es',          // re‑transcribe to Spanish
  model: 'medium',
  provider: undefined      // Whisper
});

```

### Monitoring Re-Transcription Progress

```typescript
listen('retranscription-progress', e => {
  const p = e.payload as { 
    meeting_id: string; 
    stage: string; 
    progress_percentage: number; 
    message: string 
  };
  console.log(`[${p.stage}] ${p.progress_percentage}% – ${p.message}`);
});

```

## Summary

- **Unified Pipeline**: Meetily uses identical decode-resample-VAD-transcription logic in `audio::decoder`, `audio::vad`, and `audio::common` for both initial imports and subsequent re-transcriptions.
- **Atomic Metadata**: File operations use temporary files and atomic renames to prevent corruption during interruptions.
- **Flexible Re-processing**: Re-transcription allows changing languages, models, and providers (Whisper or Parakeet) without re-importing the original audio file.
- **Concurrency Safety**: Global flags and guard patterns prevent overlapping import or re-transcription jobs.
- **Persistent Storage**: Imported audio lives in dedicated meeting folders under the recordings directory, enabling unlimited re-transcription cycles.

## Frequently Asked Questions

### What is the difference between importing audio and re-transcribing in Meetily?

Importing creates a new meeting by copying external audio into Meetily's storage and processing it for the first time, while re-transcription re-processes that already-stored audio using different transcription settings. Both operations use the same core pipeline in `audio::import.rs` and `audio::retranscription.rs`, but re-transcription skips the file copying stage and allows parameter overrides.

### How does Meetily prevent concurrent import or re-transcription jobs?

The system uses atomic flags (`IMPORT_IN_PROGRESS`, `RETRANSCRIPTION_IN_PROGRESS`) and guard structs like `ImportGuard` that set these flags when a job starts and automatically clear them when the scope ends. This mechanism prevents resource conflicts and ensures only one intensive audio processing job runs at a time.

### What happens to the original audio file when I import it into Meetily?

Meetily copies the original file into a newly created meeting folder within the recordings directory, typically naming it `audio.mp4` or preserving the original extension. The source file remains untouched in its original location, while Meetily works with the copy for all processing and subsequent re-transcription cycles.

### Can I change the transcription language or model when re-transcribing imported audio?

Yes, re-transcription accepts new `language`, `model`, and `provider` parameters that override the original import settings. You can switch from Whisper to Parakeet, change from English to Spanish, or select a different model size without re-importing the file, as implemented in `run_retranscription` (lines 100‑400 of [`retranscription.rs`](https://github.com/Zackriya-Solutions/meetily/blob/main/retranscription.rs)).