Skip to content

Connector Tools ​

Tools are the actions a connector exposes — for example, Slack's send_message, Google Drive's upload_file, or a custom SQL query tool. Each tool has a JSON Schema describing its input and output.

Tools come from two sources:

  • auto_discovered — Pulled from the connector adapter (built-in or MCP server) via sync-tools
  • manual — Created by your team on custom connector instances

Endpoints ​

MethodPathDescriptionAuth
GET/connectors/instances/:id/toolsList tools for an instanceJWT
POST/connectors/instances/:id/sync-toolsSync tools from adapterJWT + connection management permission
POST/connectors/instances/:id/toolsCreate a custom toolJWT + connection management permission
PATCH/connectors/instances/:id/tools/:toolIdEnable or disable a toolJWT + connection management permission

Syncing tools, creating custom tools, and enabling or disabling tools require management permission for the exact connection: its Personal owner, or an owner/admin of its owning Business workspace. Plan access does not replace ownership. See Who can manage an instance.


Tool Object ​

json
{
  "id": "tool_abc123",
  "connectorKey": "slack",
  "toolKey": "send_message",
  "displayName": "Send Message",
  "description": "Send a message to a Slack channel or user",
  "inputSchema": {
    "type": "object",
    "properties": {
      "channel": { "type": "string", "description": "Channel name or ID" },
      "text": { "type": "string", "description": "Message content" }
    },
    "required": ["channel", "text"]
  },
  "outputSchema": {},
  "requiresApproval": true,
  "rateLimitRpm": null,
  "isActive": true,
  "source": "auto_discovered"
}

Tool Object Fields ​

FieldTypeDescription
idstringTool ID
connectorKeystringParent connector key
toolKeystringUnique tool identifier within the connector
displayNamestringHuman-readable name
descriptionstring | nullWhat the tool does
inputSchemaobjectJSON Schema for the tool's input parameters
outputSchemaobjectJSON Schema describing the tool's output
requiresApprovalbooleanIf true, the tool can change data in the connected service. Direct execution refuses it with 403; it runs only through Chao, under Chao's approval rules
rateLimitRpmnumber | nullMaximum calls per minute; null means no limit
isActivebooleanWhether this tool is enabled on this instance
sourcestringauto_discovered or manual

GET /connectors/instances/:id/tools ​

List all tools available on a connector instance.

Request ​

Path Parameters ​

ParameterTypeDescription
idstringInstance ID

Query Parameters ​

ParameterTypeRequiredDescription
localestringNoReturn translated displayName and description for this locale (e.g. tr)

Response ​

Response Example ​

json
{
  "data": [
    {
      "id": "tool_abc123",
      "connectorKey": "slack",
      "toolKey": "send_message",
      "displayName": "Send Message",
      "description": "Send a message to a Slack channel or user",
      "inputSchema": {
        "type": "object",
        "properties": {
          "channel": { "type": "string" },
          "text": { "type": "string" }
        },
        "required": ["channel", "text"]
      },
      "outputSchema": {},
      "requiresApproval": false,
      "rateLimitRpm": null,
      "isActive": true,
      "source": "auto_discovered"
    }
  ]
}

Code Examples ​

bash
curl https://api.chainabit.com/api/v1/connectors/instances/$INSTANCE_ID/tools \
  -H "Authorization: Bearer $TOKEN"
javascript
const BASE_URL = process.env.BASE_URL;
const TOKEN = process.env.TOKEN;
const INSTANCE_ID = process.env.INSTANCE_ID;

const response = await fetch(
  `${BASE_URL}/connectors/instances/${INSTANCE_ID}/tools`,
  {
    headers: { Authorization: `Bearer ${TOKEN}` },
  },
);
const { data } = await response.json();
python
import requests, os

BASE_URL = os.environ["BASE_URL"]
TOKEN = os.environ["TOKEN"]
INSTANCE_ID = os.environ["INSTANCE_ID"]

response = requests.get(
    f"{BASE_URL}/connectors/instances/{INSTANCE_ID}/tools",
    headers={"Authorization": f"Bearer {TOKEN}"},
)
data = response.json()["data"]

POST /connectors/instances/:id/sync-tools ​

Pull the latest tool definitions from the connector adapter and upsert them into the database. For built-in connectors, this refreshes the known tool list. For MCP connectors (mcp-generic), this calls the MCP server's tools/list method.

Returns the full list of tools after sync.

Request ​

Path Parameters ​

ParameterTypeDescription
idstringInstance ID

Response ​

Response Example ​

Returns the list of tools after sync (same shape as List Tools).

json
{
  "data": [
    {
      "id": "tool_abc123",
      "connectorKey": "slack",
      "toolKey": "send_message",
      "displayName": "Send Message",
      "description": "Send a message to a Slack channel or user",
      "inputSchema": { "type": "object", "properties": { "channel": {}, "text": {} }, "required": ["channel", "text"] },
      "outputSchema": {},
      "requiresApproval": false,
      "rateLimitRpm": null,
      "isActive": true,
      "source": "auto_discovered"
    },
    {
      "id": "tool_def456",
      "connectorKey": "slack",
      "toolKey": "list_channels",
      "displayName": "List Channels",
      "description": "List all Slack channels in the workspace",
      "inputSchema": { "type": "object", "properties": {} },
      "outputSchema": {},
      "requiresApproval": false,
      "rateLimitRpm": null,
      "isActive": true,
      "source": "auto_discovered"
    }
  ]
}

Code Examples ​

bash
curl -X POST https://api.chainabit.com/api/v1/connectors/instances/$INSTANCE_ID/sync-tools \
  -H "Authorization: Bearer $TOKEN"
javascript
const response = await fetch(
  `${BASE_URL}/connectors/instances/${INSTANCE_ID}/sync-tools`,
  {
    method: "POST",
    headers: { Authorization: `Bearer ${TOKEN}` },
  },
);
const { data } = await response.json();
python
response = requests.post(
    f"{BASE_URL}/connectors/instances/{INSTANCE_ID}/sync-tools",
    headers={"Authorization": f"Bearer {TOKEN}"},
)
data = response.json()["data"]

POST /connectors/instances/:id/tools ​

Create a custom tool on a connector instance. Only available for instances of custom (non-system) connectors.

Request ​

Path Parameters ​

ParameterTypeDescription
idstringInstance ID

Request Body ​

FieldTypeRequiredDescription
toolKeystringYesUnique identifier for the tool within the connector (e.g. create_lead)
displayNamestringYesHuman-readable tool name
descriptionstringNoDescription of what the tool does
inputSchemaobjectYesJSON Schema describing required and optional input fields
outputSchemaobjectYesJSON Schema describing the expected output shape
requiresApprovalbooleanNoIf true, the tool runs only through Chao, under Chao's approval rules; direct execution refuses it (default: false)
rateLimitRpmnumberNoMaximum executions per minute (default: no limit)

Request DTO ​

json
{
  "toolKey": "create_lead",
  "displayName": "Create Lead",
  "description": "Create a new CRM lead from contact information",
  "inputSchema": {
    "type": "object",
    "properties": {
      "name": { "type": "string" },
      "email": { "type": "string", "format": "email" }
    },
    "required": ["name", "email"]
  },
  "outputSchema": {
    "type": "object",
    "properties": {
      "leadId": { "type": "string" },
      "created": { "type": "boolean" }
    }
  },
  "requiresApproval": false
}

Response ​

Response Example ​

json
{
  "data": {
    "id": "tool_ghi789",
    "connectorKey": "my-crm",
    "toolKey": "create_lead",
    "displayName": "Create Lead",
    "description": "Create a new CRM lead from contact information",
    "inputSchema": { "type": "object", "properties": { "name": {}, "email": {} }, "required": ["name", "email"] },
    "outputSchema": { "type": "object", "properties": { "leadId": {}, "created": {} } },
    "requiresApproval": false,
    "rateLimitRpm": null,
    "isActive": true,
    "source": "manual"
  }
}

Code Examples ​

bash
curl -X POST https://api.chainabit.com/api/v1/connectors/instances/$INSTANCE_ID/tools \
  -H "Authorization: Bearer $TOKEN" \
  -H "Content-Type: application/json" \
  -d '{
    "toolKey": "create_lead",
    "displayName": "Create Lead",
    "description": "Create a new CRM lead from contact information",
    "inputSchema": {
      "type": "object",
      "properties": {
        "name": { "type": "string" },
        "email": { "type": "string", "format": "email" },
        "company": { "type": "string" }
      },
      "required": ["name", "email"]
    },
    "outputSchema": {
      "type": "object",
      "properties": {
        "leadId": { "type": "string" },
        "created": { "type": "boolean" }
      }
    },
    "requiresApproval": false
  }'
javascript
const response = await fetch(
  `${BASE_URL}/connectors/instances/${INSTANCE_ID}/tools`,
  {
    method: "POST",
    headers: {
      Authorization: `Bearer ${TOKEN}`,
      "Content-Type": "application/json",
    },
    body: JSON.stringify({
      toolKey: "create_lead",
      displayName: "Create Lead",
      description: "Create a new CRM lead from contact information",
      inputSchema: {
        type: "object",
        properties: {
          name: { type: "string" },
          email: { type: "string", format: "email" },
          company: { type: "string" },
        },
        required: ["name", "email"],
      },
      outputSchema: {
        type: "object",
        properties: {
          leadId: { type: "string" },
          created: { type: "boolean" },
        },
      },
    }),
  },
);
const { data } = await response.json();
python
response = requests.post(
    f"{BASE_URL}/connectors/instances/{INSTANCE_ID}/tools",
    headers={"Authorization": f"Bearer {TOKEN}"},
    json={
        "toolKey": "create_lead",
        "displayName": "Create Lead",
        "description": "Create a new CRM lead from contact information",
        "inputSchema": {
            "type": "object",
            "properties": {
                "name": {"type": "string"},
                "email": {"type": "string", "format": "email"},
            },
            "required": ["name", "email"],
        },
        "outputSchema": {
            "type": "object",
            "properties": {
                "leadId": {"type": "string"},
                "created": {"type": "boolean"},
            },
        },
    },
)
data = response.json()["data"]

PATCH /connectors/instances/:id/tools/:toolId ​

Enable or disable a specific tool on a connector instance. Disabled tools cannot be executed.

Request ​

Path Parameters ​

ParameterTypeDescription
idstringInstance ID
toolIdstringTool ID

Request Body ​

FieldTypeRequiredDescription
enabledbooleanYestrue to enable, false to disable

Request DTO ​

json
{
  "enabled": false
}

Response ​

Response Example ​

json
{
  "data": {
    "id": "tool_abc123",
    "isActive": false
  }
}

Code Examples ​

bash
curl -X PATCH https://api.chainabit.com/api/v1/connectors/instances/$INSTANCE_ID/tools/tool_abc123 \
  -H "Authorization: Bearer $TOKEN" \
  -H "Content-Type: application/json" \
  -d '{ "enabled": false }'
bash
curl -X PATCH https://api.chainabit.com/api/v1/connectors/instances/$INSTANCE_ID/tools/tool_abc123 \
  -H "Authorization: Bearer $TOKEN" \
  -H "Content-Type: application/json" \
  -d '{ "enabled": true }'
javascript
const response = await fetch(
  `${BASE_URL}/connectors/instances/${INSTANCE_ID}/tools/tool_abc123`,
  {
    method: "PATCH",
    headers: {
      Authorization: `Bearer ${TOKEN}`,
      "Content-Type": "application/json",
    },
    body: JSON.stringify({ enabled: false }),
  },
);
const { data } = await response.json();
python
response = requests.patch(
    f"{BASE_URL}/connectors/instances/{INSTANCE_ID}/tools/tool_abc123",
    headers={"Authorization": f"Bearer {TOKEN}"},
    json={"enabled": False},
)
data = response.json()["data"]

Built with purpose.