tonhowtf/omniget · error

a chave local do SponsorBlock está corrompida

Error message

a chave local do SponsorBlock está corrompida

What it means

build_payload requires the local SponsorBlock user ID (the privateID stored locally) to be at least 30 characters after trimming. This acts as a sanity check that the stored credentials file is intact: a truncated or empty key would silently submit garbage or fail server-side, so the library refuses up front.

Solutions

  1. Regenerate/obtain the SponsorBlock private ID and re-save it, then retry.
  2. Inspect the stored key file: check it is >= 30 chars with no truncation or stray whitespace.
  3. Ensure the code path that creates the key actually ran before submit is called (no partial first-run setup).
  4. Verify the config directory is writable and not being clobbered by file sync/backup tools.

Example fix

// before
let user = config.get("sponsorblock_key").unwrap_or_default(); // ""
// after
let user = local_user_id()?; // loads or creates a valid 30+ char private ID
Defensive patterns

Strategy: validation

Validate before calling

fn has_valid_user_id(user: &str) -> bool {
    user.trim().len() >= 30
}

Type guard

fn valid_credentials(user: &str) -> Option<&str> {
    (user.trim().len() >= 30).then_some(user)
}

Try / catch

match build_payload(&id, &user, dur, &segs) {
    Err(e) if e.to_string().contains("chave local") => regenerate_and_store_key().await?,
    other => other?,
}

Prevention

When it happens

Trigger: Calling build_payload (or submit, which calls local_user_id()) when the stored SponsorBlock key is missing, empty, whitespace, or truncated to fewer than 30 characters.

Common situations: First run before the key was ever generated/saved; config file corrupted or partially written; the key copied with the tail cut off; config directory permissions or sync tools truncating the file.

Related errors


AI-assisted analysis of tonhowtf/omniget@8600b91f42 (2026-09-12). Data as JSON: /api/errors/d3523744eeb958e6. Report an issue: GitHub.

Appendix: source

Thrown at src-tauri/omniget-core/src/core/tools/sponsorblock.rs:271

        if par[1].start < par[0].end {
            return Err(anyhow!("dois trechos se sobrepõem em {:.1}s", par[1].start));
        }
    }
    Ok(())
}

/// O corpo exato do `POST /api/skipSegments`.
pub fn build_payload(
    video_id: &str,
    user_id: &str,
    duration: f64,
    segments: &[NewSegment],
) -> anyhow::Result<serde_json::Value> {
    if video_id.len() != 11 {
        return Err(anyhow!("não reconheci o vídeo do YouTube"));
    }
    if user_id.trim().len() < 30 {
        return Err(anyhow!("a chave local do SponsorBlock está corrompida"));
    }
    validate_segments(segments, duration)?;
    let segs: Vec<serde_json::Value> = segments
        .iter()
        .map(|s| {
            let mut o = serde_json::json!({
                "segment": [s.start, s.end],
                "category": s.category,
                "actionType": s.action_type,
            });
            if !s.description.trim().is_empty() {
                o["description"] = serde_json::Value::String(s.description.trim().to_string());
            }
            o
        })
        .collect();
    let mut body = serde_json::json!({
        "videoID": video_id,

View on GitHub (pinned to 8600b91f42)