Skip to main content

Query Records

Reads rows out of a table. This is the endpoint to use for pulling data into your integration -- answering a lookup, syncing a list, or polling for records that changed since the last run.

It is a POST even though it only reads. The filter is a JSON document -- a nested and/or tree with typed values -- and that does not survive a query string without inventing an encoding for nesting, types and null. The request body carries the filter shape as-is. Nothing is written.

Endpoint​

POST /integration/tables/:table/query

Authentication​

Requires a valid API token in the Authorization header.

Path Parameters​

ParameterTypeRequiredDescription
tablestringYesThe internal table name (from Get Tables)

Request Body​

All fields are optional. An empty body {} returns the first 50 rows.

FieldTypeDefaultDescription
filtersobjectnoneA filter group -- see below
selectstring[]all columnsColumn names to return
sortobject[]database order[{ "field": "fname", "direction": "desc" }] -- direction defaults to asc
pageinteger1Page number, starting at 1
per_pageinteger50Rows per page, maximum 200

Any other top-level key is rejected with 400. A misspelled perPage gets told, rather than silently returning 50 rows.

Filter groups​

A group is { "and": [...] } or { "or": [...] }. Each array item is either a condition or another group, so groups nest:

{
"filters": {
"and": [
{ "field": "fstatus", "op": "eq", "value": "open" },
{ "or": [
{ "field": "fcity", "op": "eq", "value": "חיפה" },
{ "field": "fcity", "op": "eq", "value": "תל אביב" }
] }
]
}
}

Conditions​

A condition is { "field": <column>, "op": <operator>, "value": <value> }.

Operatorvalue shapeMeaning
eq / neqscalarEqual / not equal
gt / gtescalarGreater than / greater than or equal
lt / ltescalarLess than / less than or equal
like / not_likestringSQL LIKE -- use % as the wildcard
in / not_inarray of scalars (1--200)One of / none of
betweenarray of exactly 2 scalarsInclusive range
is_null / is_not_nullomit valueColumn is / is not NULL

A scalar is a string, number, boolean, or null. An object is rejected -- there is no path for handing SQL to this endpoint.

Limits​

LimitValue
Nesting depth5 groups
Conditions per request50
Values in one in / not_in200
Rows per page200

Response​

FieldTypeDescription
tablestringThe table that was read
pagenumberThe page returned
per_pagenumberRows per page in effect
totalnumberTotal rows matching the filters, across all pages
recordsarrayThe rows

Examples​

Request​

curl -X POST "https://api.ozari.co.il/integration/tables/tcust/query" \
-H "Authorization: Bearer your-api-token-here" \
-H "Content-Type: application/json" \
-d '{
"filters": { "and": [ { "field": "fcity", "op": "eq", "value": "חיפה" } ] },
"select": ["fid", "fname", "fphone"],
"sort": [{ "field": "fname" }],
"per_page": 2
}'

Response​

{
"success": true,
"table": "tcust",
"page": 1,
"per_page": 2,
"total": 17,
"records": [
{ "fid": 12, "fname": "אבי כהן", "fphone": "050-1234567" },
{ "fid": 45, "fname": "בני לוי", "fphone": "052-7654321" }
]
}

One record by primary key​

{ "filters": { "and": [ { "field": "fid", "op": "eq", "value": 12 } ] } }

Polling for what changed​

{
"filters": { "and": [ { "field": "flastmodify", "op": "gt", "value": "2026-09-01 08:00:00" } ] },
"sort": [{ "field": "flastmodify" }]
}

Error Responses​

Every rejection names the path that caused it, so a wrong request is fixable without guessing.

Invalid table or field name​

Table and column names must match ^[A-Za-z0-9_]+$:

{
"success": false,
"error": "Invalid field name in filters.and[0]: fname)--"
}

Status: 400 Bad Request

Unsupported operator​

{
"success": false,
"error": "Unsupported operator in filters.and[0]: regexp"
}

Status: 400 Bad Request

Wrong value shape​

{
"success": false,
"error": "filters.and[0]: \"between\" needs a \"value\" array of exactly 2 scalars"
}

Status: 400 Bad Request

Table not readable​

A small set of tables hold credential material (user passwords, password-reset codes, session and impersonation records) and are never readable through this API, whatever the token:

{
"success": false,
"error": "This table is not readable through the integration API"
}

Status: 403 Forbidden

Table not found​

{
"success": false,
"error": "Table not found"
}

Status: 404 Not Found

Notes​

  • Results are scoped to the tenant the API token belongs to. There is no way to read another tenant's data.
  • per_page is capped at 200. Page through larger result sets with page, using total to know when you are done.
  • For a stable page-through, pass a sort -- without one, row order is whatever the database returns.
  • Use Get Fields to discover which column names to filter, select, and sort on.