{"record":{"id":"c72f53e65c102b51","repo":"tonhowtf/omniget","slug":"youtube-n-o-retornou-url","errorCode":null,"errorMessage":"YouTube não retornou URL","messagePattern":"YouTube não retornou URL","errorType":"exception","errorClass":"Error","httpStatus":null,"severity":"error","filePath":"src/lib/study-music/spotify-store.svelte.ts","lineNumber":155,"sourceCode":"    youtube_url: string;\n    video_id: string;\n    video_title: string;\n    channel: string;\n    score: number;\n  }>(\"study\", \"study:spotify:resolve_youtube\", {\n    title: track.title,\n    artist: track.artist,\n    durationMs: track.duration_ms ?? 0,\n    isrc: track.isrc,\n  });\n  console.log(\"[spotify-yt] resolved:\", {\n    video_id: res.video_id,\n    video_title: res.video_title,\n    channel: res.channel,\n    score: res.score,\n    url_preview: res.youtube_url?.slice(0, 100),\n  });\n  if (!res.youtube_url) throw new Error(\"YouTube não retornou URL\");\n  return res.youtube_url;\n}\n\nif (typeof window !== \"undefined\") {\n  musicPlayer.spotifyFreeFallback = resolveSpotifyToYoutube;\n}\n\nfunction mapTrack(item: any, addedAt?: string, playedAt?: string): SpotifyTrack | null {\n  const t = item?.track ?? item;\n  if (!t || !t.id) return null;\n  return {\n    id: t.id,\n    name: t.name ?? \"\",\n    uri: t.uri ?? `spotify:track:${t.id}`,\n    duration_ms: t.duration_ms ?? 0,\n    explicit: !!t.explicit,\n    is_playable: t.is_playable,\n    preview_url: t.preview_url ?? null,","sourceCodeStart":137,"sourceCodeEnd":173,"githubUrl":"https://github.com/tonhowtf/omniget/blob/8600b91f4246848bac346874daa9e61c1fc5677a/src/lib/study-music/spotify-store.svelte.ts#L137-L173","documentation":"Raised by get_guest_token in the Twitter platform module when the guest-token endpoint returns a non-2xx status. The guest token is required for anonymous API access to tweet metadata/media; without it no tweet can be resolved.","triggerScenarios":"GET to the guest token activation endpoint (with x-twitter-active-user / Accept-Language headers) returns a non-success status — 403 bot protection, 429 rate limit, 400 bad headers, 5xx outage.","commonSituations":"X/Twitter tightening anti-bot measures (403 on guest activation); guest-token endpoint deprecated or changed; datacenter IP blocked; heavy scraping triggering 429s; missing or stale public bearer token header.","solutions":["Retry with exponential backoff and jitter on 429/5xx; cache and reuse guest tokens instead of fetching per request.","On 403, expect bot protection: update headers (user-agent, bearer token) or route via authenticated cookies / a different network.","Verify the guest token endpoint URL and required auth headers are still current — this API changes frequently.","Log the response body and fall back to authenticated access (user-provided cookies) if guest access is blocked."],"exampleFix":"// before\nif !response.status().is_success() {\n    return Err(anyhow!(\"Falha ao obter guest token: HTTP {}\", response.status()));\n}\n// after\nlet status = response.status();\nif !status.is_success() {\n    let body = response.text().await.unwrap_or_default();\n    if status.as_u16() == 429 {\n        return Err(TwitterError::RateLimited); // caller retries with backoff\n    }\n    anyhow::bail!(\"Guest token HTTP {}: {}\", status, body);\n}","handlingStrategy":"retry","validationCode":null,"typeGuard":null,"tryCatchPattern":"// Cache guest tokens; back off on 429/403\nmatch get_guest_token().await {\n    Err(e) if e.to_string().contains(\"HTTP 429\") => backoff_then_retry(),\n    Err(e) if e.to_string().contains(\"HTTP 403\") => switch_to_authenticated_access(),\n    other => other,\n}","preventionTips":["Reuse and cache guest tokens instead of requesting per tweet","Keep the public bearer token and headers current — this API changes often","Add exponential backoff with jitter for 429/5xx","Prepare an authenticated-cookie fallback for when guest access is blocked","Avoid datacenter IPs that X/Twitter aggressively blocks"],"tags":["twitter","http","guest-token","api","network"],"backgroundTag":"http-error-response","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"}