Skip to main content
Glama

Search GDELT Articles

gdelt_search_articles
Read-only

Search the last 3 months of global news coverage (65+ languages) using the GDELT DOC API. Fetches up to 250 articles with URL, title, source domain, language, country, publication date, and social image URL, and returns as many as fit a 48,000-byte response — the rest are counted in withheldCount, with a continuation to reach them. Query supports full GDELT syntax: phrases ("bird flu"), boolean OR ((flu OR pandemic)), source country (sourcecountry:china), source language (sourcelang:spanish), domain (domain:who.int), GKG theme (theme:TAX_DISEASE_OUTBREAK — find identifiers with gdelt_search_themes), tone filter (tone<-5 for negative), proximity (near20:"flu virus"), and repeat (repeat3:"outbreak"). 250 is a hard per-call ceiling and GDELT offers no cursor: when a query fills it or a response comes back cut, re-query narrower startDatetime/endDatetime windows — the response hands back the exact windows to use. Note: this API covers only the most recent 3 months — use gdelt_search_tv for historical TV transcripts back to 2009.

Input Schema

TableJSON Schema
NameRequiredDescriptionDefault
sortNoSort order: relevance (default), dateDesc/dateAsc, toneDesc/toneAsc, or hybridRel (GDELT hybrid relevance and recency).relevance
queryYesSearch query. Supports GDELT operators: phrases ("bird flu"), boolean OR ((flu OR pandemic)), sourcecountry:china, sourcelang:spanish, domain:who.int, theme:TAX_DISEASE_OUTBREAK (GKG theme identifiers come from gdelt_search_themes), tone<-5, near20:"flu virus", repeat3:"outbreak".
timespanNoTime window relative to now, minimum "15min"; other examples: "24h", "7d", "1m". Ignored when startDatetime/endDatetime are set. Maximum is 3 months (the full DOC API window). Defaults to the full 3-month window.
maxRecordsNoMaximum number of articles to fetch (1–250); the response carries as many of them as fit its 48,000-byte budget. 250 is GDELT's hard per-call ceiling, not a page size — there is no cursor past it, so a query that fills 250 must be split into narrower startDatetime/endDatetime windows instead.
endDatetimeNoEnd of date range in GDELT format YYYYMMDDHHMMSS — exactly 14 digits, no separators (e.g. 20240131235959). Must be supplied together with startDatetime; supplying only one of the two is rejected.
startDatetimeNoStart of date range in GDELT format YYYYMMDDHHMMSS — exactly 14 digits, no separators (e.g. 20240101000000). Must be supplied together with endDatetime; supplying only one of the two is rejected.

Output Schema

TableJSON Schema
NameRequiredDescriptionDefault
errorNoPresent when the call failed. Absent on success.
noticeNoGuidance on an incomplete or empty result. When no articles matched, how to broaden the query or window. When GDELT returned articles dated outside an explicit startDatetime/endDatetime window, how many were dropped. When the response was cut to its 48,000-byte budget, how many articles it withheld and the route to them. When the maxRecords cap was reached on an uncut response, that more articles may exist — a higher maxRecords below the 250 ceiling, or a narrower date window at it. Absent when a non-empty result set fit under both the cap and the budget.
articlesNoMatching articles sorted per the sort parameter.
timespanNoEchoed timespan parameter when provided.
totalCountNoNumber of articles returned in this response.
withheldCountNoArticles GDELT returned inside the window that this response withheld to stay within its 48,000-byte budget — fetched minus returned, not counting articles dropped for falling outside an explicit window. Absent when every in-window article fit.
effectiveQueryNoEchoed query string for use in follow-up calls.
continuationWindowsNoWindows to re-run this query against, one at a time, when more articles are out of reach of this response. For a response cut to its budget under dateDesc or dateAsc: one window resuming from the last returned article, reaching back to the second it was published, so articles from that second come back again — or, when resuming there cannot reach a new article, one window skipping past that second. Otherwise — maxRecords at its 250 ceiling, or a cut under any other sort — the queried window halved, overlapping by one second so no article falls through the seam. Either way, de-duplicate by url. Absent when no window is known, or none would reach further.

Schema Changelog

Changes observed during successful MCP inspections.

  1. Changed1 schema field changed
    • changedInput schema / properties / query / description
      Previous value: -"Search query. Supports GDELT operators: phrases (\"bird flu\"), boolean OR ((flu OR pandemic)), sourcecountry:china, sourcelang:spanish, domain:who.int, theme:DISEASE_OUTBREAK, tone<-5, near20:\"flu virus\", repeat3:\"outbreak\"."New value: +"Search query. Supports GDELT operators: phrases (\"bird flu\"), boolean OR ((flu OR pandemic)), sourcecountry:china, sourcelang:spanish, domain:who.int, theme:TAX_DISEASE_OUTBREAK (GKG theme identifiers come from gdelt_search_themes), tone<-5, near20:\"flu virus\", repeat3:\"outbreak\"."
  2. Changed6 schema fields changed
    • changedInput schema / properties / maxRecords / description
      Previous value: -"Maximum number of articles to return (1–250). 250 is GDELT's hard per-call ceiling, not a page size — there is no cursor past it, so a query that fills 250 must be split into narrower startDatetime/endDatetime windows instead."New value: +"Maximum number of articles to fetch (1–250); the response carries as many of them as fit its 48,000-byte budget. 250 is GDELT's hard per-call ceiling, not a page size — there is no cursor past it, so a query that fills 250 must be split into narrower startDatetime/endDatetime windows instead."
    • changedOutput schema / properties / continuationWindows / description
      Previous value: -"The queried window halved, to re-run this query against one pair at a time when maxRecords is at its 250 ceiling. The halves overlap by one second so no article falls through the seam; an article published on that second can come back in both, so de-duplicate by url. Absent unless the ceiling was reached with a window that is both known and wide enough to divide."New value: +"Windows to re-run this query against, one at a time, when more articles are out of reach of this response. For a response cut to its budget under dateDesc or dateAsc: one window resuming from the last returned article, reaching back to the second it was published, so articles from that second come back again — or, when resuming there cannot reach a new article, one window skipping past that second. Otherwise — maxRecords at its 250 ceiling, or a cut under any other sort — the queried window halved, overlapping by one second so no article falls through the seam. Either way, de-duplicate by url. Absent when no window is known, or none would reach further."
    • changedOutput schema / properties / error / properties / data / properties / reason / description
      Previous value: -"Machine-readable failure mode. Declared by this tool: `no_articles`: No articles matched the query within the specified time range. `invalid_date_range`: Only one of startDatetime / endDatetime was supplied, one of them is not a real UTC calendar timestamp, or startDatetime is not earlier than endDatetime. `invalid_query`: GDELT rejected the query string as malformed — bad keyword length, unbalanced parentheses, or an illegal character. `gdelt_rate_limited`: GDELT rejected the request for its one-request-per-five-seconds limit, or too many requests were already queued for this one to start in time. `gdelt_unavailable`: GDELT DOC API is unreachable or temporarily returned no usable data. Other values are possible when a failure originates below the handler."New value: +"Machine-readable failure mode. Declared by this tool: `invalid_date_range`: Only one of startDatetime / endDatetime was supplied, one of them is not a real UTC calendar timestamp, or startDatetime is not earlier than endDatetime. `invalid_query`: GDELT rejected the query string as malformed — bad keyword length, unbalanced parentheses, or an illegal character. `gdelt_rate_limited`: GDELT rejected the request for its one-request-per-five-seconds limit, or too many requests were already queued for this one to start in time. `gdelt_unavailable`: GDELT DOC API is unreachable or temporarily returned no usable data. Other values are possible when a failure originates below the handler."
    • changedOutput schema / properties / error / properties / data / properties / reason / examples
      Previous value: -[
      -  "no_articles",
      -  "invalid_date_range",
      -  "invalid_query",
      -  "gdelt_rate_limited",
      -  "gdelt_unavailable"
      -]New value: +[
      +  "invalid_date_range",
      +  "invalid_query",
      +  "gdelt_rate_limited",
      +  "gdelt_unavailable"
      +]
    • changedOutput schema / properties / notice / description
      Previous value: -"Disclosure that the maxRecords cap was reached and more articles may exist, naming the route to them — a higher maxRecords below the 250 ceiling, or a narrower date window at it. Absent when the full result set fit under the cap."New value: +"Guidance on an incomplete or empty result. When no articles matched, how to broaden the query or window. When GDELT returned articles dated outside an explicit startDatetime/endDatetime window, how many were dropped. When the response was cut to its 48,000-byte budget, how many articles it withheld and the route to them. When the maxRecords cap was reached on an uncut response, that more articles may exist — a higher maxRecords below the 250 ceiling, or a narrower date window at it. Absent when a non-empty result set fit under both the cap and the budget."
    • addedOutput schema / properties / withheldCount
      Added value: +{
      +  "description": "Articles GDELT returned inside the window that this response withheld to stay within its 48,000-byte budget — fetched minus returned, not counting articles dropped for falling outside an explicit window. Absent when every in-window article fit.",
      +  "type": "number"
      +}
  3. Changed1 schema field changed
    • changedOutput schema / properties / error / properties / data / properties / reason / description
      Previous value: -"Machine-readable failure mode. Declared by this tool: `no_articles`: No articles matched the query within the specified time range. `invalid_date_range`: Exactly one of startDatetime / endDatetime was supplied. `invalid_query`: GDELT rejected the query string as malformed — bad keyword length, unbalanced parentheses, or an illegal character. `gdelt_rate_limited`: GDELT rejected the request for its one-request-per-five-seconds limit, or too many requests were already queued for this one to start in time. `gdelt_unavailable`: GDELT DOC API is unreachable or temporarily returned no usable data. Other values are possible when a failure originates below the handler."New value: +"Machine-readable failure mode. Declared by this tool: `no_articles`: No articles matched the query within the specified time range. `invalid_date_range`: Only one of startDatetime / endDatetime was supplied, one of them is not a real UTC calendar timestamp, or startDatetime is not earlier than endDatetime. `invalid_query`: GDELT rejected the query string as malformed — bad keyword length, unbalanced parentheses, or an illegal character. `gdelt_rate_limited`: GDELT rejected the request for its one-request-per-five-seconds limit, or too many requests were already queued for this one to start in time. `gdelt_unavailable`: GDELT DOC API is unreachable or temporarily returned no usable data. Other values are possible when a failure originates below the handler."
  4. Changed1 schema field changed
    • changedOutput schema / properties / error / properties / data / properties / reason / description
      Previous value: -"Machine-readable failure mode. Declared by this tool: `no_articles`: No articles matched the query within the specified time range. `invalid_date_range`: Exactly one of startDatetime / endDatetime was supplied. `invalid_query`: GDELT rejected the query string as malformed — bad keyword length, unbalanced parentheses, or an illegal character. `gdelt_rate_limited`: GDELT rejected the request because its one-request-per-five-seconds limit was reached. `gdelt_unavailable`: GDELT DOC API is unreachable or temporarily returned no usable data. Other values are possible when a failure originates below the handler."New value: +"Machine-readable failure mode. Declared by this tool: `no_articles`: No articles matched the query within the specified time range. `invalid_date_range`: Exactly one of startDatetime / endDatetime was supplied. `invalid_query`: GDELT rejected the query string as malformed — bad keyword length, unbalanced parentheses, or an illegal character. `gdelt_rate_limited`: GDELT rejected the request for its one-request-per-five-seconds limit, or too many requests were already queued for this one to start in time. `gdelt_unavailable`: GDELT DOC API is unreachable or temporarily returned no usable data. Other values are possible when a failure originates below the handler."
  5. Changed2 schema fields changed
    • changedInput schema / properties / sort / description
      Previous value: -"Sort order: relevance (default), date (newest first), social (most socially shared)."New value: +"Sort order: relevance (default), dateDesc/dateAsc, toneDesc/toneAsc, or hybridRel (GDELT hybrid relevance and recency)."
    • changedInput schema / properties / sort / enum
      Previous value: -[
      -  "date",
      -  "relevance",
      -  "social"
      -]New value: +[
      +  "relevance",
      +  "dateDesc",
      +  "dateAsc",
      +  "toneDesc",
      +  "toneAsc",
      +  "hybridRel"
      +]
  6. Changed3 schema fields changed
    • changedInput schema / properties / timespan / description
      Previous value: -"Time window relative to now, e.g. \"24h\", \"7d\", \"1m\". Ignored when startDatetime/endDatetime are set. Maximum is 3 months (the full DOC API window). Defaults to the full 3-month window."New value: +"Time window relative to now, minimum \"15min\"; other examples: \"24h\", \"7d\", \"1m\". Ignored when startDatetime/endDatetime are set. Maximum is 3 months (the full DOC API window). Defaults to the full 3-month window."
    • changedOutput schema / properties / error / properties / data / properties / reason / description
      Previous value: -"Machine-readable failure mode. Declared by this tool: `no_articles`: No articles matched the query within the specified time range. `invalid_date_range`: Exactly one of startDatetime / endDatetime was supplied. `invalid_query`: GDELT rejected the query string as malformed — bad keyword length, unbalanced parentheses, or an illegal character. `gdelt_unavailable`: GDELT DOC API is unreachable or rate-limited. Other values are possible when a failure originates below the handler."New value: +"Machine-readable failure mode. Declared by this tool: `no_articles`: No articles matched the query within the specified time range. `invalid_date_range`: Exactly one of startDatetime / endDatetime was supplied. `invalid_query`: GDELT rejected the query string as malformed — bad keyword length, unbalanced parentheses, or an illegal character. `gdelt_rate_limited`: GDELT rejected the request because its one-request-per-five-seconds limit was reached. `gdelt_unavailable`: GDELT DOC API is unreachable or temporarily returned no usable data. Other values are possible when a failure originates below the handler."
    • changedOutput schema / properties / error / properties / data / properties / reason / examples
      Previous value: -[
      -  "no_articles",
      -  "invalid_date_range",
      -  "invalid_query",
      -  "gdelt_unavailable"
      -]New value: +[
      +  "no_articles",
      +  "invalid_date_range",
      +  "invalid_query",
      +  "gdelt_rate_limited",
      +  "gdelt_unavailable"
      +]
  7. Changed6 schema fields changed
    • changedInput schema / $schema
      Previous value: -"http://json-schema.org/draft-07/schema#"New value: +"https://json-schema.org/draft/2020-12/schema"
    • addedInput schema / additionalProperties
      Added value: +false
    • changedOutput schema / $schema
      Previous value: -"http://json-schema.org/draft-07/schema#"New value: +"https://json-schema.org/draft/2020-12/schema"
    • addedOutput schema / anyOf
      Added value: +[
      +  {
      +    "not": {
      +      "required": [
      +        "error"
      +      ]
      +    },
      +    "required": [
      +      "articles",
      +      "effectiveQuery",
      +      "totalCount"
      +    ]
      +  },
      +  {
      +    "required": [
      +      "error"
      +    ]
      +  }
      +]
    • addedOutput schema / properties / error
      Added value: +{
      +  "additionalProperties": {},
      +  "description": "Present when the call failed. Absent on success.",
      +  "properties": {
      +    "code": {
      +      "description": "JSON-RPC error code for this failure.",
      +      "maximum": 9007199254740991,
      +      "minimum": -9007199254740991,
      +      "type": "integer"
      +    },
      +    "data": {
      +      "additionalProperties": {},
      +      "properties": {
      +        "reason": {
      +          "description": "Machine-readable failure mode. Declared by this tool: `no_articles`: No articles matched the query within the specified time range. `invalid_date_range`: Exactly one of startDatetime / endDatetime was supplied. `invalid_query`: GDELT rejected the query string as malformed — bad keyword length, unbalanced parentheses, or an illegal character. `gdelt_unavailable`: GDELT DOC API is unreachable or rate-limited. Other values are possible when a failure originates below the handler.",
      +          "examples": [
      +            "no_articles",
      +            "invalid_date_range",
      +            "invalid_query",
      +            "gdelt_unavailable"
      +          ],
      +          "type": "string"
      +        },
      +        "recovery": {
      +          "additionalProperties": {},
      +          "description": "Actionable next step for the caller.",
      +          "properties": {
      +            "hint": {
      +              "type": "string"
      +            }
      +          },
      +          "required": [
      +            "hint"
      +          ],
      +          "type": "object"
      +        },
      +        "retryable": {
      +          "description": "Whether retrying may succeed.",
      +          "type": "boolean"
      +        }
      +      },
      +      "type": "object"
      +    },
      +    "message": {
      +      "description": "Human-readable description of what went wrong.",
      +      "type": "string"
      +    }
      +  },
      +  "required": [
      +    "code",
      +    "message"
      +  ],
      +  "type": "object"
      +}
    • removedOutput schema / required
      Removed value: -[
      -  "articles",
      -  "effectiveQuery",
      -  "totalCount"
      -]
  8. Changed3 schema fields changed
    • changedInput schema / properties / maxRecords / description
      Previous value: -"Maximum number of articles to return (1–250)."New value: +"Maximum number of articles to return (1–250). 250 is GDELT's hard per-call ceiling, not a page size — there is no cursor past it, so a query that fills 250 must be split into narrower startDatetime/endDatetime windows instead."
    • addedOutput schema / properties / continuationWindows
      Added value: +{
      +  "description": "The queried window halved, to re-run this query against one pair at a time when maxRecords is at its 250 ceiling. The halves overlap by one second so no article falls through the seam; an article published on that second can come back in both, so de-duplicate by url. Absent unless the ceiling was reached with a window that is both known and wide enough to divide.",
      +  "items": {
      +    "additionalProperties": false,
      +    "description": "One window to re-query with the same query string.",
      +    "properties": {
      +      "endDatetime": {
      +        "description": "End of this window in GDELT format YYYYMMDDHHMMSS.",
      +        "type": "string"
      +      },
      +      "startDatetime": {
      +        "description": "Start of this window in GDELT format YYYYMMDDHHMMSS.",
      +        "type": "string"
      +      }
      +    },
      +    "required": [
      +      "startDatetime",
      +      "endDatetime"
      +    ],
      +    "type": "object"
      +  },
      +  "type": "array"
      +}
    • changedOutput schema / properties / notice / description
      Previous value: -"Recovery hint when no articles matched — echoes filters and suggests how to broaden. Absent on successful responses."New value: +"Disclosure that the maxRecords cap was reached and more articles may exist, naming the route to them — a higher maxRecords below the 250 ceiling, or a narrower date window at it. Absent when the full result set fit under the cap."
  9. Changed4 schema fields changed
    • changedInput schema / properties / endDatetime / description
      Previous value: -"End of date range in GDELT format YYYYMMDDHHMMSS (e.g. 20240131235959). Must be used together with startDatetime."New value: +"End of date range in GDELT format YYYYMMDDHHMMSS — exactly 14 digits, no separators (e.g. 20240131235959). Must be supplied together with startDatetime; supplying only one of the two is rejected."
    • addedInput schema / properties / endDatetime / pattern
      Added value: +"^\\d{14}$"
    • changedInput schema / properties / startDatetime / description
      Previous value: -"Start of date range in GDELT format YYYYMMDDHHMMSS (e.g. 20240101000000). Must be used together with endDatetime."New value: +"Start of date range in GDELT format YYYYMMDDHHMMSS — exactly 14 digits, no separators (e.g. 20240101000000). Must be supplied together with endDatetime; supplying only one of the two is rejected."
    • addedInput schema / properties / startDatetime / pattern
      Added value: +"^\\d{14}$"
  10. Changed5 schema fields changed
    • addedOutput schema / properties / effectiveQuery
      Added value: +{
      +  "description": "Echoed query string for use in follow-up calls.",
      +  "type": "string"
      +}
    • removedOutput schema / properties / query
      Removed value: -{
      -  "description": "Echoed query string for use in follow-up calls.",
      -  "type": "string"
      -}
    • addedOutput schema / properties / totalCount
      Added value: +{
      +  "description": "Number of articles returned in this response.",
      +  "type": "number"
      +}
    • removedOutput schema / properties / totalReturned
      Removed value: -{
      -  "description": "Number of articles returned in this response.",
      -  "type": "number"
      -}
    • changedOutput schema / required
      Previous value: -[
      -  "articles",
      -  "totalReturned",
      -  "query"
      -]New value: +[
      +  "articles",
      +  "effectiveQuery",
      +  "totalCount"
      +]
  11. First observed

TDQS

A4.7/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond the readOnlyHint and openWorldHint annotations, it discloses a 48,000-byte response budget, withheldCount with a continuation for overflow, a hard 250-per-call ceiling, the absence of a cursor, and how cut responses should be handled. This is substantive operational context that determines whether the agent trusts result counts.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is long but appropriately so: scope, returned fields and truncation behavior, query syntax, pagination strategy, and the historical alternative each take one focused block. It is front-loaded with the core purpose and contains no filler or vague marketing language.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given an output schema, rich input schema, and annotations covering side effects, the description covers the remaining operational essentials: time-window limits, result truncation and continuation, hard ceilings, and query syntax. An agent has enough to invoke it correctly and plan around GDELT's no-cursor limitation.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, and each parameter is already well documented with operators, formats, defaults, and constraints, so the description does not need to compensate. The prose mostly restates the 250 ceiling and window-splitting behavior that the maxRecords schema description already contains, adding little new per-parameter meaning.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The first sentence names the action ('Search'), the resource ('last 3 months of global news coverage'), the backing API ('GDELT DOC API'), and the language scope (65+), then lists the concrete fields returned. It explicitly contrasts with gdelt_search_tv at the end, so the tool is distinguishable from its nearest sibling without opening schemas.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description states both when to use this tool (recent 3-month news search) and when not to ('use gdelt_search_tv for historical TV transcripts back to 2009'). It also gives a concrete strategy for the pagination-limited case (re-query narrower startDatetime/endDatetime windows) and points to gdelt_search_themes for theme identifier lookup.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

Try in Browser

Glama MCP Gateway

Add one secure layer between your agents and this server.