> Source: https://wexa.ai/docs/data-tables/query-table-rows

# query-table-rows

Read rows from a Data Table, with paging, sorting, free-text search and filters. Rows come back keyed by `column_id`. Needs the `fabric:table.read` grant.

**Query rows**

**Wexa MCP server**

```bash
curl -sS -X POST https://fabric.wexa.ai/mcp/$FABRIC_PROJECT_ID \
  -H "authorization: Bearer $FABRIC_API_KEY" \
  -H "Mcp-Session-Id: $MCP_SESSION_ID" \
  -H "content-type: application/json" -H "accept: application/json" \
  -d '{"jsonrpc":"2.0","id":3,"method":"tools/call","params":{"name":"query-table-rows","arguments":{"table_id":"6ab1944e7566f41b5c28e2eb","page":1,"page_size":3}}}'
```

```json
{
  "content": [
    {
      "type": "text",
      "text": "{\"lifecycle_id\":\"qlc_000196\",\"result\":{\"table_id\":\"6ab1944e7566f41b5c28e2eb\",\"page\":1,\"page_size\":3,\"total_count\":2,\"rows\":[{\"_id\":\"6ab1945e7566f41b5c28e301\",\"row_id\":1,\"6ab1944e12917e3705beb0b9\":true,\"6ab1944e56ac670306c8deed\":120,\"6ab1944eb6557622b2632872\":\"Acme\"},{\"_id\":\"6ab1945e7566f41b5c28e302\",\"row_id\":2,\"6ab1944e12917e3705beb0b9\":false,\"6ab1944e56ac670306c8deed\":75,\"6ab1944eb6557622b2632872\":\"Globex\"}]}}"
    }
  ],
  "isError": false
}
```

**REST API**

```bash
curl -sS https://fabric.wexa.ai/v1/query-table-rows \
  -H "authorization: Bearer $FABRIC_API_KEY" \
  -H "content-type: application/json" \
  -d '{"table_id":"6ab1944e7566f41b5c28e2eb","page":1,"page_size":3}'
```

```json
{
  "lifecycle_id": "qlc_000196",
  "result": {
    "table_id": "6ab1944e7566f41b5c28e2eb",
    "page": 1,
    "page_size": 3,
    "total_count": 2,
    "rows": [
      {
        "_id": "6ab1945e7566f41b5c28e301",
        "row_id": 1,
        "6ab1944e12917e3705beb0b9": true,
        "6ab1944e56ac670306c8deed": 120,
        "6ab1944eb6557622b2632872": "Acme"
      },
      {
        "_id": "6ab1945e7566f41b5c28e302",
        "row_id": 2,
        "6ab1944e12917e3705beb0b9": false,
        "6ab1944e56ac670306c8deed": 75,
        "6ab1944eb6557622b2632872": "Globex"
      }
    ]
  }
}
```

**TypeScript SDK**

```ts
import { Fabric } from '@wexa-fabric/sdk'

const fabric = new Fabric()
const result = await fabric.queryTableRows({
  table_id: '6ab1944e7566f41b5c28e2eb',
  page: 1,
  page_size: 3
})
```

```ts
// result is the payload itself, with no `.result` to read
{
  table_id: '6ab1944e7566f41b5c28e2eb',
  page: 1,
  page_size: 3,
  total_count: 2,
  rows: [
    {
      _id: '6ab1945e7566f41b5c28e301',
      row_id: 1,
      "6ab1944e12917e3705beb0b9": true,
      "6ab1944e56ac670306c8deed": 120,
      "6ab1944eb6557622b2632872": 'Acme'
    },
    {
      _id: '6ab1945e7566f41b5c28e302',
      row_id: 2,
      "6ab1944e12917e3705beb0b9": false,
      "6ab1944e56ac670306c8deed": 75,
      "6ab1944eb6557622b2632872": 'Globex'
    }
  ]
}
```

**Python SDK**

```python
from wexa import Fabric

fabric = Fabric()
out = fabric.query_table_rows(table_id="6ab1944e7566f41b5c28e2eb", page=1, page_size=3)
```

```python
# out is the result, already unwrapped
{
    "table_id": "6ab1944e7566f41b5c28e2eb",
    "page": 1,
    "page_size": 3,
    "total_count": 2,
    "rows": [
        {
            "_id": "6ab1945e7566f41b5c28e301",
            "row_id": 1,
            "6ab1944e12917e3705beb0b9": True,
            "6ab1944e56ac670306c8deed": 120,
            "6ab1944eb6557622b2632872": "Acme"
        },
        {
            "_id": "6ab1945e7566f41b5c28e302",
            "row_id": 2,
            "6ab1944e12917e3705beb0b9": False,
            "6ab1944e56ac670306c8deed": 75,
            "6ab1944eb6557622b2632872": "Globex"
        }
    ]
}
```

## Parameters

| Parameter | Type | Required | Notes |
| --- | --- | --- | --- |
| `table_id` | string | Required | Table id from `list-tables`, a 24-character hex id. A table in this project. |
| `page` | integer | Optional | 1-based page number. Default 1. A value below 1 is refused. |
| `page_size` | integer | Optional | Rows per page. Default 50. |
| `sort_key` | string | Optional | Column to sort by. |
| `sort` | integer | Optional | `1` ascending, `-1` descending. Any other value is refused. |
| `search` | string | Optional | Free-text search across the table. |
| `search_filters` | array | Optional | Filters over the table's columns, each `{column, operator, value, type}`; a malformed entry is refused. `column`, `operator` and `value` are required. `column` is a column name or a `column_id`. `operator` is one of `eq`, `gt`, `gte`, `in`, `lt`, `lte`, `ne`, `nin`; `value` is an array for `in` and `nin`. `type` is the column type, e.g. string, number or datetime. Default string. |

**Show full response**

A real response, captured from a live call to `query-table-rows`:

**Result of query-table-rows**

**REST API**

```json
{
  "lifecycle_id": "qlc_000196",
  "result": {
    "page": 1,
    "page_size": 3,
    "rows": [
      {
        "6ab1944e12917e3705beb0b9": true,
        "6ab1944e56ac670306c8deed": 120,
        "6ab1944eb6557622b2632872": "Acme",
        "_id": "6ab1945e7566f41b5c28e301",
        "coworker_user_id": "6a79a770b6c128ccc24bfca7",
        "row_id": 1
      },
      {
        "6ab1944e12917e3705beb0b9": false,
        "6ab1944e56ac670306c8deed": 75,
        "6ab1944eb6557622b2632872": "Globex",
        "_id": "6ab1945e7566f41b5c28e302",
        "coworker_user_id": "6a79a770b6c128ccc24bfca7",
        "row_id": 2
      }
    ],
    "table_id": "6ab1944e7566f41b5c28e2eb",
    "total_count": 2
  }
}
```

**TypeScript SDK**

```ts
// the object you get back IS the result — there is no `.result` to read
{
  page: 1,
  page_size: 3,
  rows: [
    {
      '6ab1944e12917e3705beb0b9': true,
      '6ab1944e56ac670306c8deed': 120,
      '6ab1944eb6557622b2632872': 'Acme',
      _id: '6ab1945e7566f41b5c28e301',
      coworker_user_id: '6a79a770b6c128ccc24bfca7',
      row_id: 1
    },
    {
      '6ab1944e12917e3705beb0b9': false,
      '6ab1944e56ac670306c8deed': 75,
      '6ab1944eb6557622b2632872': 'Globex',
      _id: '6ab1945e7566f41b5c28e302',
      coworker_user_id: '6a79a770b6c128ccc24bfca7',
      row_id: 2
    }
  ],
  table_id: '6ab1944e7566f41b5c28e2eb',
  total_count: 2
}

// The TS SDK names these camelCase — lifecycleId, traceId — where Python uses
// lifecycle_id and trace_id. Both are non-enumerable: readable, but omitted by
// Object.keys() and JSON.stringify(). `result.lifecycleId` here is undefined.
result.lifecycleId // 'qlc_000196'
```

**Python SDK**

```python
# a dict subclass; `result` is already unwrapped
{
 "page": 1,
 "page_size": 3,
 "rows": [
  {
   "6ab1944e12917e3705beb0b9": True,
   "6ab1944e56ac670306c8deed": 120,
   "6ab1944eb6557622b2632872": "Acme",
   "_id": "6ab1945e7566f41b5c28e301",
   "coworker_user_id": "6a79a770b6c128ccc24bfca7",
   "row_id": 1
  },
  {
   "6ab1944e12917e3705beb0b9": False,
   "6ab1944e56ac670306c8deed": 75,
   "6ab1944eb6557622b2632872": "Globex",
   "_id": "6ab1945e7566f41b5c28e302",
   "coworker_user_id": "6a79a770b6c128ccc24bfca7",
   "row_id": 2
  }
 ],
 "table_id": "6ab1944e7566f41b5c28e2eb",
 "total_count": 2
}

out.lifecycle_id  # 'qlc_000196' — an attribute, not a key
```

**More details**

The result has `rows`, `page`, `page_size`, `table_id` and `total_count`. Each row's `_id` is the `row_id` that `update-table-row` and `delete-table-rows` take; the integer `row_id` field in a row is not.

To run an agent against the next matching row of a table, see [Schedules](/docs/automation/create-schedule).

Not marked consequential: it is audited lightly and the project's write gate never holds it.

Every tool call works the same way: [How every tool call works](/docs/sdks-and-apis/how-every-tool-call-works).
