curl --request POST \
--url https://ndi-api.nace.ai/v1/workspaces/{workspace_id}/tools/run-sql \
--header 'Content-Type: application/json' \
--header 'X-API-Key: <api-key>' \
--data '
{
"sql": "<string>"
}
'{
"result": {
"handle": "<string>",
"row_count": 123,
"columns": [],
"path": "<string>",
"preview_truncated": false,
"rows": []
},
"sql": "<string>",
"duplicate": false,
"result_citation": {
"result_file": {
"download_url": "<string>",
"download_url_expires_at": "2023-11-07T05:31:56Z",
"file_id": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"file_name": "<string>",
"format": "parquet",
"handle": "<string>",
"path": "<string>",
"preview_url": "<string>",
"row_count": 123
},
"source_paths": [
"<string>"
],
"sql": "<string>",
"grounding": {
"sql": "<string>",
"columns": [
{
"data_type": "<string>",
"name": "<string>"
}
],
"grounding_reason": "<string>",
"grounding_status": "exact",
"preview_truncated": false,
"regions": [
{
"a1_range": "<string>",
"source_path": "<string>",
"basis": "verified",
"bounding": false,
"kind": "sheet",
"matched_rows": 0,
"scan_index": 123,
"scan_label": "<string>",
"sheet_name": "<string>"
}
],
"result_id": "<string>",
"row_count": 0,
"rows": [
{}
],
"source_paths": [
"<string>"
],
"supports_answer": true,
"verified": false
}
},
"result_materialization_error": "<string>",
"source_paths": [
"<string>"
]
}{
"error": {
"code": "invalid_request",
"detail": null,
"message": "Request body has extra fields that this operation does not accept.",
"request_id": "req-01j9k2n3p4q5r6s7t8v9",
"retryable": false
}
}{
"error": {
"code": "invalid_request",
"detail": null,
"message": "Request body has extra fields that this operation does not accept.",
"request_id": "req-01j9k2n3p4q5r6s7t8v9",
"retryable": false
}
}run_sql
Run one caller-authored read-only SELECT over the workspace’s tables.
Cost class: fast. No planner and no answering agent — the statement
runs directly in the guarded SQL engine, against every queryable tab in
the workspace registered as a view under the table_name that
file-metadata and the folder-metadata table census publish. Joins
across files are ordinary SQL joins; earlier run-sql results are
registered too, so a returned res_… handle can be joined, aggregated,
or paged with LIMIT/OFFSET in the next statement.
The full result is retained as parquet whatever the preview shows —
result_citation.result_file.download_url fetches it whole. A
statement that is not a read, or reads an unregistered table, is refused
with invalid_request naming the rule broken and the registered
tables. For a natural-language question — or when the answer should be
composed and cited for you — use query-tables instead.
curl --request POST \
--url https://ndi-api.nace.ai/v1/workspaces/{workspace_id}/tools/run-sql \
--header 'Content-Type: application/json' \
--header 'X-API-Key: <api-key>' \
--data '
{
"sql": "<string>"
}
'{
"result": {
"handle": "<string>",
"row_count": 123,
"columns": [],
"path": "<string>",
"preview_truncated": false,
"rows": []
},
"sql": "<string>",
"duplicate": false,
"result_citation": {
"result_file": {
"download_url": "<string>",
"download_url_expires_at": "2023-11-07T05:31:56Z",
"file_id": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"file_name": "<string>",
"format": "parquet",
"handle": "<string>",
"path": "<string>",
"preview_url": "<string>",
"row_count": 123
},
"source_paths": [
"<string>"
],
"sql": "<string>",
"grounding": {
"sql": "<string>",
"columns": [
{
"data_type": "<string>",
"name": "<string>"
}
],
"grounding_reason": "<string>",
"grounding_status": "exact",
"preview_truncated": false,
"regions": [
{
"a1_range": "<string>",
"source_path": "<string>",
"basis": "verified",
"bounding": false,
"kind": "sheet",
"matched_rows": 0,
"scan_index": 123,
"scan_label": "<string>",
"sheet_name": "<string>"
}
],
"result_id": "<string>",
"row_count": 0,
"rows": [
{}
],
"source_paths": [
"<string>"
],
"supports_answer": true,
"verified": false
}
},
"result_materialization_error": "<string>",
"source_paths": [
"<string>"
]
}{
"error": {
"code": "invalid_request",
"detail": null,
"message": "Request body has extra fields that this operation does not accept.",
"request_id": "req-01j9k2n3p4q5r6s7t8v9",
"retryable": false
}
}{
"error": {
"code": "invalid_request",
"detail": null,
"message": "Request body has extra fields that this operation does not accept.",
"request_id": "req-01j9k2n3p4q5r6s7t8v9",
"retryable": false
}
}Authorizations
Path Parameters
Workspace identifier.
Body
One read-only SELECT over the workspace's queryable tables.
Table names come from metadata — file-metadata publishes each
queryable tab's table_name and folder-metadata's table census
lists them all — and from earlier run-sql results (every response's
res_… handle is a registered table on the next call, so results can
be joined, aggregated, or paged with LIMIT/OFFSET). Joins across files
are ordinary SQL joins. A statement that is not a read, or that reads an
unregistered table, is refused with invalid_request naming the rule
and the registered tables.
1 - 4096Response
Successful Response
One executed statement: shape, bounded preview, and the retained result.
The stored result is complete whatever the preview shows;
result_citation.result_file.download_url fetches the whole parquet.
duplicate marks a statement answered from an earlier identical run's
stored result — free, and safe to build on.
One retained result table with a bounded inline preview.
Show child attributes
Show child attributes
The normalized statement that ran — the result's provenance.
Provenance for one generated TablesQA result file.
Show child attributes
Show child attributes
The uploaded files the statement read — carried on the response itself so source attribution survives when no result file is materialized (job-attributed agent statements).