<!-- BusyBot node reference — https://busybot.net/tools/grist/ -->

> Node: Grist (`grist`) · Action · v1
> Category: Data & Storage · Credentials: Grist API (`gristApi`)
> Updated: 2026-08-16

# Grist

> Perform CRUD operations on Grist table rows

## Overview

Grist is an open-source modern relational spreadsheet platform that combines the flexibility of a spreadsheet with the power of a database. This tool interacts with the Grist REST API to create, read, update, and delete rows in Grist document tables. It supports filtering and sorting when retrieving rows, and offers two data input modes: auto-mapping from incoming data, or manually defining field values.

**Category:** Data & Storage  
**Tool Name:** `grist`  
**Version:** 1

**Appearance:** Icon: `lucide-Table` | Color: `#36B973`

## Node Type

**Action** — processes input items and produces output

## Input / Output

| Direction | Port(s) |
|-----------|--------|
| Input | `Input` |
| Output | `Output`, `Error` |

## Credentials

This tool requires **Grist API** credentials.
See the [Credentials Guide](https://busybot.net/credentials/grist-api/) for setup instructions.

### Operations

| Operation | Value | Description |
|-----------|-------|-------------|
| Create Row | `create` | Create rows in a table |
| Delete Row | `delete` | Delete rows from a table |
| Get Many Rows | `getAll` | Read rows from a table |
| Update Row | `update` | Update rows in a table |

### Parameters

#### Create Row (`create`)

| Parameter | Type | Required | Default | Description |
|-----------|------|----------|---------|-------------|
| Data to Send | `options` | No | `defineInNode` | Whether to insert the input data this node receives in the new row. |
| | | | | Options: `autoMapInputs` (use when node input properties match destination column names), `defineInNode` (set the value for each destination column) |
| Inputs to Ignore | `string` | No | — | List of input properties to avoid sending, separated by commas. Leave empty to send all properties. _(shown when Data to Send is `autoMapInputs`)_ |
| Fields to Send | `fixedCollection` | No | `{}` | Column name and value pairs to send to Grist. _(shown when Data to Send is `defineInNode`)_ |
| — Column Name (`fieldId`) | `string` | No | — | The column name (ID) to set. Use the column identifier as shown in Code View. |
| — Field Value | `string` | No | — | The value to set for this column. Supports expressions like {{ $json.name }}. |

#### Delete Row (`delete`)

| Parameter | Type | Required | Default | Description |
|-----------|------|----------|---------|-------------|
| Row ID | `string` | Yes | — | ID of the row to delete, or comma-separated list of row IDs to delete. Supports expressions. |

#### Get Many Rows (`getAll`)

| Parameter | Type | Required | Default | Description |
|-----------|------|----------|---------|-------------|
| Return All | `boolean` | No | `false` | Whether to return all results or only up to a given limit. |
| Limit | `number` | No | `50` | Max number of results to return. _(shown when Return All is `false`)_ |
| Additional Options | `collection` | No | `{}` | Additional filtering and sorting options. |
| — Filter | `fixedCollection` | No | `{}` | Only return rows matching all of the given filters. For complex filters, create a formula column and filter for the value "true". |
| — Column Name (`field`) | `string` | Yes | — | Column name to apply the filter on. Use the column ID as shown in Code View. |
| — Values | `string` | No | — | Comma-separated list of values to search for in the filtered column. |
| — Sort Order | `fixedCollection` | No | `{}` | Columns to sort the returned rows by. |
| — Column Name (`field`) | `string` | Yes | — | Column name to sort on. Use the column ID as shown in Code View. |
| — Direction | `options` | No | `asc` | Direction to sort in. |
| | | | | Options: `asc`, `desc` |

#### Update Row (`update`)

| Parameter | Type | Required | Default | Description |
|-----------|------|----------|---------|-------------|
| Row ID | `string` | Yes | — | ID of the row to update. Supports expressions like {{ $json.rowId }}. |
| Data to Send | `options` | No | `defineInNode` | Whether to insert the input data this node receives in the new row. |
| | | | | Options: `autoMapInputs` (use when node input properties match destination column names), `defineInNode` (set the value for each destination column) |
| Inputs to Ignore | `string` | No | — | List of input properties to avoid sending, separated by commas. Leave empty to send all properties. _(shown when Data to Send is `autoMapInputs`)_ |
| Fields to Send | `fixedCollection` | No | `{}` | Column name and value pairs to send to Grist. _(shown when Data to Send is `defineInNode`)_ |
| — Column Name (`fieldId`) | `string` | No | — | The column name (ID) to set. Use the column identifier as shown in Code View. |
| — Field Value | `string` | No | — | The value to set for this column. Supports expressions like {{ $json.status }}. |

#### All Operations

| Parameter | Type | Required | Default | Description |
|-----------|------|----------|---------|-------------|
| Document ID | `string` | Yes | — | In your document, click your profile icon, then Document Settings, then copy the value under "This document's ID". |
| Table ID | `string` | Yes | — | ID of table to operate on. If unsure, look at the Code View in Grist. |
| Max Concurrency | `number` | No | `10` | Maximum number of items to process concurrently. |

## Output Data

The result is merged into the input item's JSON, so the incoming fields remain available downstream. Binary data on the input item is forwarded unchanged.

| Operation | Output |
|-----------|--------|
| `create` | One item. `id` — the row ID Grist assigned — plus every column value that was sent. |
| `update` | One item. `id` — the row you targeted — plus every column value that was sent. |
| `delete` | One item carrying `success: true`. |
| `getAll` | **One item per returned row**, each carrying `id` plus one property per table column. When the query matches nothing, the input item is passed through unchanged. |

A row read back from a table therefore looks like this:

```json
{
  "id": 12,
  "Name": "Ada Lovelace",
  "Status": "active",
  "Signed_Up": "2024-01-15"
}
```

Column properties use the column **ID** as shown in Grist's Code View, which is not always the label displayed in the grid. Address them downstream with expressions such as `{{ $json.Status }}`.

## Usage Examples

- Create a new row in a Grist table
- Retrieve all rows from a Grist document table
- Update a row in a Grist spreadsheet
- Delete rows by ID from a Grist table

## Example Configuration

Read every row of a table:

```json
{
  "type": "grist",
  "parameters": {
    "operation": "getAll",
    "docId": "abc123DocId",
    "tableId": "Users",
    "returnAll": true
  }
}
```

Read a filtered, sorted page of rows:

```json
{
  "type": "grist",
  "parameters": {
    "operation": "getAll",
    "docId": "abc123DocId",
    "tableId": "Orders",
    "returnAll": false,
    "limit": 20,
    "additionalOptions": {
      "filter": {
        "filterProperties": [
          { "field": "status", "values": "pending" },
          { "field": "priority", "values": "high" }
        ]
      },
      "sort": {
        "sortProperties": [
          { "field": "createdAt", "direction": "desc" }
        ]
      }
    }
  }
}
```

Create a row from the incoming item, dropping two properties:

```json
{
  "type": "grist",
  "parameters": {
    "operation": "create",
    "docId": "abc123DocId",
    "tableId": "ImportedData",
    "dataToSend": "autoMapInputs",
    "inputsToIgnore": "id,createdAt"
  }
}
```

Create a row from explicitly named columns:

```json
{
  "type": "grist",
  "parameters": {
    "operation": "create",
    "docId": "abc123DocId",
    "tableId": "Users",
    "dataToSend": "defineInNode",
    "fieldsToSend": {
      "properties": [
        { "fieldId": "name", "fieldValue": "{{ $json.fullName }}" },
        { "fieldId": "email", "fieldValue": "{{ $json.email }}" },
        { "fieldId": "status", "fieldValue": "active" }
      ]
    }
  }
}
```

Update one column of an existing row:

```json
{
  "type": "grist",
  "parameters": {
    "operation": "update",
    "docId": "abc123DocId",
    "tableId": "UserProfiles",
    "rowId": "{{ $json.rowId }}",
    "dataToSend": "defineInNode",
    "fieldsToSend": {
      "properties": [
        { "fieldId": "status", "fieldValue": "inactive" }
      ]
    }
  }
}
```

Delete several rows in one call:

```json
{
  "type": "grist",
  "parameters": {
    "operation": "delete",
    "docId": "abc123DocId",
    "tableId": "Users",
    "rowId": "123,456,789"
  }
}
```

### Error Handling

| Mode | Behavior |
|------|----------|
| **stop** | Halts workflow on first error |
| **continue** | Skips failed items, passes successful ones through |
| **errorPort** | Routes failed items to Error output port |

## Tips

Create, read, update, or delete rows in Grist spreadsheet database tables using the Grist REST API.

- **Document ID and Table ID are always required.** The document ID is in Document Settings under "This document's ID"; the table ID is the identifier shown in Grist's Code View, which can differ from the tab label.
- **Use column IDs, not labels.** Filter, sort and field parameters all address columns by their Code View identifier.
- **Two ways to supply data.** `autoMapInputs` sends the incoming item's properties straight through, which suits imports where the item already matches the table; `defineInNode` lets you name each column and its value explicitly. With `defineInNode`, at least one field must be defined or the item fails.
- **Delete accepts a list.** A comma-separated Row ID deletes several rows in one call.
- **Filters match values, not expressions.** Each filter entry is a column plus a comma-separated list of accepted values, and all filters must match. For anything more complex, add a formula column in Grist and filter it for `true`.
- **Get Many Rows fans out.** Each returned row becomes its own item, so downstream nodes process rows individually with no Split Out node needed.