# Search API operations (`search_operations`)

Searches every Sign Customiser partner API operation by keyword, resource family, verb class or required scope, and returns each match stable operation id, summary, required scope, whether it mutates, its parameter and request-body schema, its response schema and a documentation link. It is the discovery step before any execute_read, execute_create, execute_update or execute_delete call, because those take an operation id and nothing else identifies one. It changes nothing and requires the mcp:advanced scope.

- Source URL: https://www.signcustomiser.com/help/mcp/tools/search_operations/
- Markdown URL: https://www.signcustomiser.com/help/mcp/tools/search_operations.md
- MCP endpoint: https://web.signcustomiser.com/mcp
- Required scope: none beyond a connected store
- Only visible to a connection granted `mcp:advanced`. Naming it without that scope answers `insufficient_scope`.
- Behaviour: read

## Purpose

Find the partner API operation that does what you need, and the exact arguments it takes, before running it through an executor.

## Annotations

| Hint | Value |
| --- | --- |
| readOnlyHint | true |
| destructiveHint | false |
| idempotentHint | true |
| openWorldHint | false |

## Prerequisites

- A merchant has connected this store and approved mcp:advanced.
- Either a query, or at least one of the resource, verb_class and scope filters. An unfiltered empty query is refused rather than answered with an arbitrary page.

## Arguments

| Property | Type | Required | Description |
| --- | --- | --- | --- |
| `query` | string | no | Words to match against operation ids, summaries, paths and descriptions. Matches are ranked, and an operation matching no word is left out rather than padded in. |
| `resource` | string | no | Restrict to one resource family, which is the first path segment after /api/v3 — for example customisers, orders, webhook-subscriptions. |
| `verb_class` | string | no | Restrict to one class of operation. read covers every GET and every validation-only operation; the other three name the executor that runs them. Closed set. One of: `read`, `create`, `update`, `delete`. |
| `scope` | string | no | Restrict to operations requiring one /api/v3 scope. Closed set of 13 values. One of: `customisers:read`, `customisers:write`, `pricing:read`, `pricing:write`, `products:read`, `products:write`, `orders:read`, `orders:write`, `quotes:read`, `webhooks:read`, `webhooks:write`, `store:read`, `analytics:read`. |
| `limit` | integer | no | How many matches to return, 1 to 50. Defaults to 10. Each match carries full schemas, so a large page is a large response. |

## Result

Up to limit matches, highest relevance first, each carrying the operation id an executor takes, the scope it needs, the executor that owns it, its schemas and its documentation URL. total_matches and truncated say whether the page is all of them.

| Property | Type | Required | Description |
| --- | --- | --- | --- |
| `request_id` | string | yes | The API request id, for support. |
| `store` | object | yes | The Store this connection resolved to. |
| `store.id` | integer | no |  |
| `store.name` | string | no |  |
| `operations` | array of object | yes | The matches, highest relevance first. |
| `operations[].operation_id` | string | no | The id an executor takes. |
| `operations[].summary` | string | no | One line. |
| `operations[].resource` | string | no |  |
| `operations[].verb_class` | string | no | One of: `read`, `create`, `update`, `delete`. |
| `operations[].executor` | string | no | The tool that runs this operation. |
| `operations[].scope` | string | no | The /api/v3 scope the connection also needs. mcp:advanced alone authorises nothing. One of: `customisers:read`, `customisers:write`, `pricing:read`, `pricing:write`, `products:read`, `products:write`, `orders:read`, `orders:write`, `quotes:read`, `webhooks:read`, `webhooks:write`, `store:read`, `analytics:read`. |
| `operations[].idempotency` | string | no | Whether the operation requires, accepts or refuses an idempotency_key. One of: `none`, `optional`, `required`. |
| `operations[].destructive` | boolean | no |  |
| `operations[].open_world` | boolean | no | True when the operation reaches beyond the store own data. |
| `operations[].dry_run_operation_id` | string | no | The validate twin a dry run reaches, or null where the operation has none. |
| `operations[].docs_url` | string | no |  |
| `total_matches` | integer | yes | How many operations matched, before the page limit. |
| `truncated` | boolean | yes | True when total_matches is larger than this page. |

## Error cases

| Code | Recovery |
| --- | --- |
| `insufficient_scope` | The connection was approved without mcp:advanced. Ask the merchant to reconnect and approve the advanced tools. |
| `required` | Neither a query nor a filter was sent. Send at least one. |
| `validation_failed` | A resource family the API does not have. The error repeats every family in allowed_values. A verb_class or scope outside its published enum is refused earlier still, as a JSON-RPC -32602 naming the property. |

## Example: Find the font-tier operations no curated tool covers

Request:

```json
{
  "jsonrpc": "2.0",
  "id": 1,
  "method": "tools/call",
  "params": {
    "name": "search_operations",
    "arguments": {
      "query": "font tier",
      "verb_class": "create",
      "limit": 1
    }
  }
}
```

Response:

```json
{
  "jsonrpc": "2.0",
  "id": 1,
  "result": {
    "structuredContent": {
      "request_id": "req_01jz9x2k7c8f3m5n6p7q8r9s0t",
      "store": {
        "id": 12,
        "name": "Demo Signs"
      },
      "operations": [
        {
          "operation_id": "createFontTier",
          "summary": "Create a font tier",
          "resource": "customisers",
          "verb_class": "create",
          "executor": "execute_create",
          "scope": "pricing:write",
          "idempotency": "required",
          "destructive": false,
          "open_world": false,
          "dry_run_operation_id": "validateCreateFontTier",
          "docs_url": "https://www.signcustomiser.com/help/api/v3-post-create-a-font-tier/"
        }
      ],
      "total_matches": 3,
      "truncated": true
    }
  }
}
```

## Example: A resource family the API does not have (error)

Request:

```json
{
  "jsonrpc": "2.0",
  "id": 1,
  "method": "tools/call",
  "params": {
    "name": "search_operations",
    "arguments": {
      "resource": "unicorns"
    }
  }
}
```

Response:

```json
{
  "jsonrpc": "2.0",
  "id": 1,
  "result": {
    "isError": true,
    "structuredContent": {
      "error": {
        "code": "validation_failed",
        "title": "Validation failed",
        "detail": "The request could not be completed.",
        "recovery": "Correct every field listed in errors, using its pointer to locate the value and allowed_values where one is given, then call the tool again.",
        "allowed_values": [
          "customisers",
          "orders",
          "products"
        ]
      }
    }
  }
}
```
