{"record":{"id":"4d9e425bb88e8d62","repo":"tonhowtf/omniget","slug":"marque-pelo-menos-um-trecho-antes-de-enviar","errorCode":null,"errorMessage":"marque pelo menos um trecho antes de enviar","messagePattern":"marque pelo menos um trecho antes de enviar","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"src-tauri/omniget-core/src/core/tools/sponsorblock.rs","lineNumber":208,"sourceCode":"    pub start: f64,\n    pub end: f64,\n    pub category: String,\n    #[serde(default = \"default_action\")]\n    pub action_type: String,\n    /// Só o capítulo usa: é o título que aparece na barra.\n    #[serde(default)]\n    pub description: String,\n}\n\nfn default_action() -> String {\n    \"skip\".to_string()\n}\n\n/// Recusa o que o servidor recusaria, com a mensagem em português e antes de\n/// gastar um envio (o limite de taxa é por conta, não por tentativa válida).\npub fn validate_segments(segments: &[NewSegment], duration: f64) -> anyhow::Result<()> {\n    if segments.is_empty() {\n        return Err(anyhow!(\"marque pelo menos um trecho antes de enviar\"));\n    }\n    if segments.len() > MAX_SEGMENTS_PER_SUBMIT {\n        return Err(anyhow!(\n            \"no máximo {} trechos por envio\",\n            MAX_SEGMENTS_PER_SUBMIT\n        ));\n    }\n    for (i, s) in segments.iter().enumerate() {\n        let n = i + 1;\n        if !CATEGORIES.contains(&s.category.as_str()) {\n            return Err(anyhow!(\n                \"trecho {}: categoria desconhecida ({})\",\n                n,\n                s.category\n            ));\n        }\n        if !ACTION_TYPES.contains(&s.action_type.as_str()) {\n            return Err(anyhow!(","sourceCodeStart":190,"sourceCodeEnd":226,"githubUrl":"https://github.com/tonhowtf/omniget/blob/8600b91f4246848bac346874daa9e61c1fc5677a/src-tauri/omniget-core/src/core/tools/sponsorblock.rs#L190-L226","documentation":"Client-side pre-flight check in `validate_segments` that rejects an empty segments list. It mirrors what the SponsorBlock server would reject anyway, so the failure surfaces in Portuguese before spending a submission against the per-account rate limit.","triggerScenarios":"Calling `validate_segments(&[], duration)` (directly or via `build_payload`) when the user submitted a segment submission with no marked segments.","commonSituations":"UI bug clearing the segment list before submit; user clicking 'send' before dragging any timestamps; programmatic callers passing an empty Vec.","solutions":["Ensure at least one NewSegment with valid start/end times is present before calling build_payload/validate_segments.","In the UI, disable the submit button until a segment is marked.","If validating in a test, populate the segments slice with sample data."],"exampleFix":"// before\nvalidate_segments(&[], duration)?;\n// after\nlet segs = vec![NewSegment { category: \"sponsor\".into(), action_type: \"skip\".into(), start: 10.0, end: 30.0, description: String::new() }];\nvalidate_segments(&segs, duration)?;","handlingStrategy":"validation","validationCode":"if segments.is_empty() {\n    return Err(\"mark at least one segment before submitting\".into());\n}","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Disable the submit button until at least one segment is marked.","Never call build_payload with a programmatically empty Vec.","Validate UI state before constructing the payload."],"tags":["validation","sponsorblock","empty-input"],"backgroundTag":"empty-required-field","analyzedSha":"8600b91f4246848bac346874daa9e61c1fc5677a","analyzedAt":"2026-09-12T14:29:19.317Z","contentChangedAt":"2026-09-12T14:29:19.317Z","schemaVersion":2},"datasetVersion":"2026-09-15T23:17:13.987Z"}