gitbutlerapp/gitbutler · error · anyhow::Error

Failed to get signature for but, requested version may be to

Error message

Failed to get signature for but, requested version may be too old

What it means

Thrown in install_linux.rs when download_to_string(&signature_url) fails while fetching the detached signature for the but CLI binary. On Linux the CLI and its signature are located by convention (base of the AppImage URL + artifact name), so a 404 or network error downloading the .sig file surfaces as this context-wrapped error, with 'requested version may be too old' hinting that older releases never published CLI signatures.

Source

Thrown at crates/but-installer/src/install_linux.rs:53

        .ok_or_else(|| anyhow::anyhow!("Failed to construct but cli URL"))?;
    let download_url = format!("{base_download_url}/{filename}");
    let signature_url = format!("{download_url}.sig");

    validate_download_url(&signature_url)?;
    validate_download_url(&download_url)?;
    info(&format!("Download URL: {download_url}"));

    let temp_dir = tempfile::Builder::new()
        .prefix("gitbutler-install.")
        .tempdir()?;
    let tmp_filepath = temp_dir.path().join(filename);

    info(&format!("Downloading GitButler {}...", release.version));
    download_file(&download_url, &tmp_filepath)?;
    info("Download completed successfully");

    let signature_b64 = download_to_string(&signature_url).with_context(|| {
        anyhow!("Failed to get signature for but, requested version may be too old")
    })?;
    verify_signature(&tmp_filepath, &signature_b64, temp_dir.path())?;

    // Install the app bundle
    install_app(&tmp_filepath, &config.home_dir, channel)?;

    Ok(())
}

fn install_app(but_path: &Path, home_dir: &Path, channel: Option<Channel>) -> Result<()> {
    let install_bin_path = but_binary_path(home_dir);
    let bin_dir = install_bin_path
        .parent()
        .ok_or_else(|| anyhow!("Failed to resolve bin dir path"))?;
    fs::create_dir_all(bin_dir)?;

    let but_backup = if install_bin_path.is_file() {
        let suffix: u64 = std::time::SystemTime::now()

View on GitHub (pinned to caf1f223d3)

Solutions

  1. Install a more recent release (or latest/nightly) — versions that predate CLI signature publishing cannot be verified.
  2. Check that signature_url (base of the AppImage URL with the 'but' artifact) actually resolves, e.g. curl -f -I <signature_url>.
  3. Retry the install to rule out a transient network/CDN error.
  4. If behind a proxy, ensure it does not block the signature file while allowing the binary.
Defensive patterns

Strategy: retry

Validate before calling

// Before install, probe the convention-derived signature URL
fn signature_exists(base: &str) -> bool {
    let sig = format!("{base}/but.sig");
    reqwest::blocking::Client::new().head(&sig).map(|r| r.status().is_success()).unwrap_or(false)
}

Try / catch

match download_to_string(&signature_url) {
    Ok(sig) => verify_signature(&tmp_filepath, &sig, temp_dir.path())?,
    Err(e) => {
        warn("signature unavailable (release too old?); retry with latest release");
        return Err(e.context("Failed to get signature for but"));
    },
}

Prevention

When it happens

Trigger: Installing a release old enough that no signature file was published for the but binary at the convention-derived signature_url; the CDN returning 404/5xx for the signature; a network failure or proxy blocking the second download after the binary itself downloaded fine.

Common situations: Pinning to an old VersionRequest::Specific version; using a local mirror or CI network that lets the AppImage through but blocks the .sig; a transient releases CDN outage mid-install.

Related errors


AI-assisted analysis of gitbutlerapp/gitbutler@caf1f223d3 (2026-08-20). Data as JSON: /api/errors/d7f3637da02f1381. Report an issue: GitHub.