v2
latestOpenAPI 3.1.0Proprietary2026-08-05143259.2 KBList news (cursor-paginated)
Feed of enriched articles, newest first. Default filter: relevance_score >= 4 AND at least one active ticker. Pagination is cursor-based with a default page size of 10 (any size from 1 to 20 via page_size=; Pro keys go up to 50): omit cursor for the newest page, then pass the next_cursor from each response to fetch the next (older) page. next_cursor: null means the end of the feed. Cursors are opaque — do not construct or parse them; an invalid cursor returns 400. Archive depth is tiered: paging back past your plan's horizon (Free 30 days, Basic 90, Pro 180) returns 403 with an upgrade hint.
Delta polling (sort=ingested): the same feed ordered by the moment rows became available, for "what is new since my last poll". Articles reach the feed later than their publish time (collection median ~30 min for general news, with a long tail), so a poller that filters by time_published misses most late arrivals; sort=ingested never misses a row. First call without cursor returns the newest page_size rows and a cursor at the feed head; each later call with the previous next_cursor returns only rows added since. In this mode next_cursor is always non-null — empty results means you are caught up, keep the cursor and poll again later (responses are cached for 60 s, so polling more often than once a minute buys nothing). New rows only: an update to an already-delivered article is not re-sent. time_published is not monotonic within a delta page; sort client-side if you need chronological order. A cursor is only valid with the sort mode that issued it.
Keeping up. One call returns at most page_size rows, so a poller holds its position at the head only while calls per day × page_size stays above the daily volume of the stream it asked for. Below that it falls a little further behind every day, and the symptom misleads: time_published reads hours or days old while the data is current. What went stale is the cursor, not the feed. So drain instead of polling once per tick: when a page comes back with results filled, call again immediately, and sleep only once results is empty. That clears a burst within the same cycle and lets a poller catch up by itself after downtime. Two levers if the call budget is still short, and they multiply: page_size (up to 20, or 50 on a Pro key) and a narrower stream (min_relevance, symbol, category). For scale, at the default >= 4 floor the feed carries roughly 2,700 rows a day, while min_relevance=7 carries roughly 1,000.
A poller that never catches up eventually meets the archive gate: the 403 below is keyed on the age of the first row you have not read yet, so it fires on a delta poller that never paged back at all.
Query parameters
Opaque cursor from a prior response's next_cursor. Omit for the newest page.
Filter to articles that mention this ticker. US equities use the bare symbol (NVDA); cryptocurrencies use the <SYM>-USD form (BTC-USD), and a bare crypto name resolves to it (DOGE matches DOGE-USD); foreign listings use the Yahoo suffix (VOD.L). A delisted symbol returns its news history. A renamed company's current ticker also matches articles tagged with its former ticker, and any share class of an issuer matches articles tagged with its other listed classes (GOOGL includes rows tagged GOOG); article tags stay as published.
Keep only these categories. Accepts a single value, a CSV list (category=earnings,insider), or a repeated parameter — matches any of them (OR).
Drop these categories from the feed. Same single / CSV / repeated forms as category.
Override the default ≥4 threshold.
Items per page, default 10. Any value from 1 to 20 is accepted on every tier; 21-50 requires a Pro key. A value outside 1-50, or an over-20 page without a Pro key, returns 400 — the page is never silently clamped. Pagination is otherwise unchanged: pass each response's next_cursor back as cursor regardless of page size.
story collapses coverage of one event to a single representative row (the story root): syndicated reprints and independently written articles about the same event, matched on headline and lead similarity. Populates the story_id, sources_count and sources fields on each item. Omit for the full feed (every article, story fields null). Only story is accepted; any other value returns 400. Note: row-level filters (symbol, category, min_relevance) apply to the story's representative root, so a story whose root does not match the filter is omitted entirely.
published (default) is the reverse-chronological feed. ingested is delta-polling mode: rows in the order they became available, ascending, with next_cursor always returned (empty results = caught up) — see the endpoint description. All other filters apply unchanged in both modes. Cursors are mode-specific: a cursor is only valid with the sort mode that issued it (a mismatch returns 400).
Response
A page of enriched articles.
Example response
{
"results": [
{
"enrichment": {
"tickers": [
"NVDA"
],
"news_context_enhancement": {
"key_entities": [
{
"type": "company"
}
]
}
},
"story_id": "788e477c66f3849b",
"sources_count": 3,
"sources": [
"reuters.com",
"apnews.com",
"bloomberg.com"
],
"insider": {
"transaction_code": "S",
"shares": "25000",
"avg_price_usd": "187.32",
"total_value_usd": "4683000",
"insider_name": "STEVENS MARK A",
"insider_title": "Director",
"transaction_date": "2026-07-09",
"filed_at": "2026-07-11T20:31:04Z"
}
}
]
}