tonhowtf/omniget · error
Post not found via GQL
Error message
Post not found via GQL
What it means
request_gql posts to Instagram's graphql/query endpoint (PolarisPostActionLoadPostQueryQuery) and looks for the media payload under data.xdt_shortcode_media (or the legacy data.shortcode_media). This error is thrown when the HTTP response succeeded but neither key exists or the value is JSON null — i.e. Instagram accepted the query but returned no media node for the requested shortcode. It usually means Instagram refused to serve the post anonymously (login wall, deleted/private post) or the GQL doc-id/headers are stale.
Solutions
- Verify the post is public and exists by opening it in a browser/incognito before retrying.
- Check that GQL_DOC_ID, x-ig-app-id and the anonymous cookie flow are up to date; update them if Instagram rotated the endpoint.
- Log the raw JSON response at the failure point to see whether Instagram returned an error message or challenge instead of data.
- Rely on the existing fallback chain (request_embed then fallback_ytdlp) — ensure the ytdlp fallback is available and up to date.
- Add retries with backoff for transient rate-limit responses rather than treating every failure as permanent.
Example fix
// before
let media = data.get("xdt_shortcode_media").or_else(|| data.get("shortcode_media"));
// after
let media = data
.get("xdt_shortcode_media")
.or_else(|| data.get("shortcode_media"))
.filter(|m| !m.is_null())
.with_context(|| format!("GQL returned no media for post; keys={:?}", data.as_object().map(|o| o.keys().collect::<Vec<_>>())))?; Defensive patterns
Strategy: fallback
Validate before calling
// Rust: check the URL looks like a canonical post before calling
fn looks_like_post(url: &str) -> bool {
url.contains("/p/") || url.contains("/reel/") || url.contains("/tv/")
} Type guard
fn has_media_node(data: &serde_json::Value) -> bool {
data.get("data")
.and_then(|d| d.get("xdt_shortcode_media").or_else(|| d.get("shortcode_media")))
.map(|m| !m.is_null())
.unwrap_or(false)
} Try / catch
match downloader.get_media_info(url).await {
Ok(info) => use(info),
Err(e) if e.to_string().contains("Post not found via GQL") => {
// post is private/deleted or GQL schema changed; use embed or yt-dlp fallback
fallback_extract(url).await
}
Err(e) => return Err(e),
} Prevention
- Only pass canonical public post/reel URLs
- Keep GQL doc_id and app-id headers updated when Instagram rotates them
- Always wire the embed/yt-dlp fallback path
- Log raw GQL responses to detect schema changes early
When it happens
Trigger: Calling get_media_info on an Instagram post/reel whose GQL response has data but data.xdt_shortcode_media and data.shortcode_media are absent or null; non-existent or deleted shortcode; private account; Instagram rate-limiting or login-walling the anonymous query.
Common situations: Instagram changed the GraphQL schema or doc_id so the key was renamed; the anonymous cookie/app-id became invalid; post is from a private account; post was deleted between URL validation and fetch; heavy scraping caused a soft-block returning an empty data object.
Understand the failure class
Background: "invalid response format", "malformed payload", "missing data field": when an API returns 200 but the response shape is wrong — this error's family across 23 libraries.
Related errors
- No media found in post
- download falhou: HTTP {}
- Twitch GQL respondeu HTTP {}
- nao achei os bundles JS do X na pagina
- baixei os bundles do X mas nao achei operacoes GraphQL neles
AI-assisted analysis of tonhowtf/omniget@8600b91f42 (2026-09-12).
Data as JSON: /api/errors/a1e6afba175949ba.
Report an issue: GitHub.
Appendix: source
Thrown at src-tauri/omniget-core/src/platforms/instagram.rs:438
.await?;
if !response.status().is_success() {
return Err(anyhow!("Instagram GQL retornou HTTP {}", response.status()));
}
let json: serde_json::Value = response.json().await?;
let data = json
.get("data")
.ok_or_else(|| anyhow!("Resposta GQL sem data"))?;
let media = data
.get("xdt_shortcode_media")
.or_else(|| data.get("shortcode_media"));
match media {
Some(m) if !m.is_null() => Ok(m.clone()),
_ => Err(anyhow!("Post not found via GQL")),
}
}
async fn request_embed(&self, post_id: &str) -> anyhow::Result<serde_json::Value> {
let url = format!("https://www.instagram.com/p/{}/embed/captioned/", post_id);
let response = self
.client
.get(&url)
.header(
"Accept",
"text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8",
)
.header("Accept-Language", "en-GB,en;q=0.9")
.header("Sec-Fetch-Dest", "iframe")
.header("Sec-Fetch-Mode", "navigate")
.header("Sec-Fetch-Site", "cross-site")
.header("Referer", "https://www.instagram.com/")View on GitHub (pinned to 8600b91f42)