Fetch bounded rows for a dataflow
fetchReturn bounded rows for a dataflow — the completion path for hosted clients.
Use this when the client cannot execute a client-download plan locally (no
shell/filesystem — e.g. a hosted store app or connector) but still needs
actual values. fetch server-side downloads the exact GET/fan-out plan
build_url would produce, concatenates it, runs one bounded literal-equality
query, and releases the artifact — the raw dataset never enters model context.
Clients that CAN execute locally should keep using ask/build_url and run
the plan themselves; fetch is the affinity-free hosted shortcut, not the
power path.
POST-only selections have no hosted download path: fetch raises
fetch_shape_unsupported and the caller must execute the build_url plan
client-side. A rejected/over-length selection raises the same reason
build_url would report; narrow the selection and retry.
fetch does not page, deliberately. It holds no dataset between calls:
every call rebuilds the plan, re-downloads every part from the provider, and
releases the artifact. An offset over that would be unsound as well as
wasteful — there is no snapshot behind the cursor, so rows shifting upstream
between calls would silently skip or duplicate observations, and N pages
would mean N full downloads of the same dataflow from an agency that may
rate-limit. When a result is truncated, narrow it (select, where,
time_range) or switch to stage_url + query_dataset, which pages
with offset over ONE immutable staged artifact and downloads once.
no_records_for_selection is TERMINAL, not a fault: the request was
well-formed and the source holds no observations for it. Widen the selection
or state that no data exists — do not retry the same selection. Only
upstream_origin_error (an origin fault) and upstream_rate_limited
are worth retrying.
Args: agency_id: SDMX agency code, e.g. "ABS", "ESTAT", "OECD" dataflow_id: SDMX dataflow identifier, e.g. "ERP_Q" selections: Optional {dimension_id: [code or name, ...]} to anchor the query time_range: Optional time filter (e.g. "2020-2024", "since 2015", "2024") precision: URL breadth — "point", "series" (default), or "cube" availability: "confirmed" (default) or "best_effort" select: Optional list of columns to return (defaults to all columns) where: Optional {column: value | [values]} literal-equality row filters limit: Optional max rows to return (a safe default applies when omitted) max_bytes: Optional smaller byte budget for this response; it can only lower the server ceiling, never raise it response_format: Which channel carries the rows. "auto" (default) means no preference and lets the server decide; "text" sends them as CSV in the text channel only, "structured" as typed rows only, "both" in both. If you got a summary but no rows, call again with response_format="text".
Input Schema
| Name | Required | Description | Default |
|---|---|---|---|
| limit | No | ||
| where | No | ||
| select | No | ||
| agency_id | Yes | ||
| max_bytes | No | ||
| precision | No | series | |
| selections | No | ||
| time_range | No | ||
| dataflow_id | Yes | ||
| availability | No | confirmed | |
| response_format | No | auto |
Output Schema
| Name | Required | Description | Default |
|---|---|---|---|
| rows | No | ||
| columns | No | ||
| agency_id | Yes | ||
| truncated | Yes | ||
| dataflow_id | Yes | ||
| limit_source | Yes | ||
| matched_rows | Yes | ||
| applied_limit | Yes | ||
| returned_rows | Yes | ||
| max_bytes_ceiling | No | ||
| min_bytes_required | No | ||
| source_request_count | Yes |