Zackriya-Solutions/meetily · warning · anyhow::Error

Unsupported model

Error message

Unsupported model: {}

What it means

download_model maps a fixed set of model names to official ggerganov/whisper.cpp HuggingFace URLs via a match; any other string hits the default arm and is rejected before any network I/O. Supported keys: tiny, base, small, medium, large-v3-turbo, large-v3, tiny-q5_1, base-q5_1, small-q5_1, medium-q5_0, large-v3-turbo-q5_0, large-v3-q5_0. Matching is exact and case-sensitive.

Solutions

  1. Use one of the exact supported keys listed above, byte-for-byte
  2. Fetch the model list from the engine (get_whisper_models) and only offer those ids in the UI
  3. To add a new model, extend both this match arm with its URL and the frontend catalog, keeping the ggml-<key>.bin naming convention

Example fix

// before
await invoke('download_model', { modelName: 'medium-q5_1' }); // unsupported

// after
await invoke('download_model', { modelName: 'medium-q5_0' }); // real key
Defensive patterns

Strategy: validation

Validate before calling

const SUPPORTED = ['tiny','base','small','medium','large-v3-turbo','large-v3',
  'tiny-q5_1','base-q5_1','small-q5_1','medium-q5_0','large-v3-turbo-q5_0','large-v3-q5_0'];
if (!SUPPORTED.includes(modelName)) {
  throw new Error(`Unsupported model '${modelName}'. Supported: ${SUPPORTED.join(', ')}`);
}
await invoke('download_model', { modelName });

Type guard

const isSupportedModel = (name: string): name is typeof SUPPORTED[number] =>
  SUPPORTED.includes(name as any);

Try / catch

try {
  await invoke('download_model', { modelName });
} catch (e) {
  if (String(e).includes('Unsupported model')) { showSupportedModelList(); } else { throw e; }
}

Prevention

When it happens

Trigger: Passing 'large' or 'turbo' (not real keys); casing mistakes like 'Base'; wrong quantization suffix ('medium-q5_1' does not exist — only medium-q5_0); passing an arbitrary HuggingFace repo id.

Common situations: Frontend model list out of sync with the Rust catalog after a version update; user typing a custom model name; scripts hardcoding names from older releases (e.g. 'large-v2' was never added here).

Related errors


AI-assisted analysis of Zackriya-Solutions/meetily@a2cb62e827 (2026-09-12). Data as JSON: /api/errors/2e0ddbaccc31fc44. Report an issue: GitHub.

Appendix: source

Thrown at frontend/src-tauri/src/whisper_engine/whisper_engine.rs:1089

    }

    pub async fn download_model(&self, model_name: &str, progress_callback: Option<Box<dyn Fn(u8) + Send>>) -> Result<()> {
        log::info!("Starting download for model: {}", model_name);

        let model_url = match model_name {
            "tiny" => "https://huggingface.co/ggerganov/whisper.cpp/resolve/main/ggml-tiny.bin",
            "base" => "https://huggingface.co/ggerganov/whisper.cpp/resolve/main/ggml-base.bin",
            "small" => "https://huggingface.co/ggerganov/whisper.cpp/resolve/main/ggml-small.bin",
            "medium" => "https://huggingface.co/ggerganov/whisper.cpp/resolve/main/ggml-medium.bin",
            "large-v3-turbo" => "https://huggingface.co/ggerganov/whisper.cpp/resolve/main/ggml-large-v3-turbo.bin",
            "large-v3" => "https://huggingface.co/ggerganov/whisper.cpp/resolve/main/ggml-large-v3.bin",
            "tiny-q5_1" => "https://huggingface.co/ggerganov/whisper.cpp/resolve/main/ggml-tiny-q5_1.bin",
            "base-q5_1" => "https://huggingface.co/ggerganov/whisper.cpp/resolve/main/ggml-base-q5_1.bin",
            "small-q5_1" => "https://huggingface.co/ggerganov/whisper.cpp/resolve/main/ggml-small-q5_1.bin",
            "medium-q5_0" => "https://huggingface.co/ggerganov/whisper.cpp/resolve/main/ggml-medium-q5_0.bin",
            "large-v3-turbo-q5_0" => "https://huggingface.co/ggerganov/whisper.cpp/resolve/main/ggml-large-v3-turbo-q5_0.bin",
            "large-v3-q5_0" => "https://huggingface.co/ggerganov/whisper.cpp/resolve/main/ggml-large-v3-q5_0.bin",
            _ => return Err(anyhow!("Unsupported model: {}", model_name)),
        };

        self.download_model_from_url(model_name, model_url, progress_callback).await
    }

    async fn download_model_from_url(
        &self,
        model_name: &str,
        model_url: &str,
        progress_callback: Option<Box<dyn Fn(u8) + Send>>,
    ) -> Result<()> {
        let active_download = self.reserve_active_download(model_name).await?;
        let file_path = self.models_dir.join(format!("ggml-{}.bin", model_name));

        let result = self
            .download_model_with_owner(
                model_name,
                model_url,

View on GitHub (pinned to a2cb62e827)