Integrator API

The Integrator API enables B2B partners to resell Snipara to their clients with isolated workspaces, dedicated API keys, and configurable resource limits.

Partner Program Only

The Integrator API is available to approved partners. Apply to the Partner Program to get started.

Overview

The Integrator system has a hierarchical structure:

Integrator (B2B Partner)
└── Workspace (white-label container)
    ├── Client A (end-user)
    │   ├── Project (isolated Snipara project)
    │   └── API Keys (snipara_ic_*)
    ├── Client B
    │   ├── Project
    │   └── API Keys
    └── Webhooks (client lifecycle events)

Authentication

All Integrator API endpoints require your standard Snipara API key with integrator permissions. You must be logged in as an approved integrator.

curl -H "Authorization: Bearer YOUR_SESSION_TOKEN" https://www.snipara.com/api/integrator/...

For MCP Server access (api.snipara.com), use your team API key with the X-API-Key header.

Base URLs

ServiceBase URLUse Case
Web Apphttps://www.snipara.com/api/integratorDashboard operations (requires session)
MCP Serverhttps://api.snipara.com/v1/integratorProgrammatic access (requires API key)

Integrator Tiers

TierPriceClient Limit
STARTER$99/mo10 clients
GROWTH$249/mo50 clients
SCALE$499/mo200 clients
ENTERPRISECustomUnlimited

Client Bundles

Each client is assigned a bundle that determines their resource limits:

BundlePriceQueries/moMemoriesSwarmsAgents/SwarmDocumentsStorage
LITE$19/mo5001001550100 MB
STANDARD$49/mo5,0005005102001 GB
UNLIMITED$99/moUnlimitedUnlimitedUnlimited20Unlimited10 GB

Workspace API

Get Workspace

GET /api/integrator/workspace

Returns your workspace details, including client count and limits.

Response

{
  "success": true,
  "data": {
    "id": "ws_abc123",
    "name": "Acme Workspace",
    "slug": "acme",
    "webhookUrl": "https://acme.com/webhooks/snipara",
    "hasWebhookSecret": true,
    "clientCount": 5,
    "clientLimit": 10,
    "tier": "STARTER"
  }
}

Create Workspace

POST /api/integrator/workspace
{
  "name": "Acme Workspace",
  "slug": "acme"  // lowercase, alphanumeric + hyphens only
}

Update Workspace

PATCH /api/integrator/workspace
{
  "name": "New Name",  // optional
  "webhookUrl": "https://...",  // optional
  "webhookSecret": "your-secret"  // optional
}

Clients API

List Clients

GET /api/integrator/clients?limit=50&offset=0&is_active=true&bundle=STANDARD

Query Parameters

  • limit - Results per page (default: 50, max: 100)
  • offset - Pagination offset
  • is_active - Filter by status: true or false
  • bundle - Filter by bundle: LITE, STANDARD, UNLIMITED

Response

{
  "success": true,
  "data": {
    "clients": [
      {
        "id": "client_456",
        "projectId": "proj_789",
        "projectSlug": "acme-client-a",
        "name": "Client A",
        "email": "admin@clienta.com",
        "externalId": "cust_123",
        "bundle": "STANDARD",
        "isActive": true,
        "limits": { "queries_per_month": 2000, ... }
      }
    ],
    "pagination": { "total": 5, "limit": 50, "offset": 0, "hasMore": false }
  }
}

Create Client

POST /api/integrator/clients
{
  "name": "Client A",
  "email": "admin@clienta.com",
  "external_id": "cust_123",  // optional, your internal ID
  "bundle": "STANDARD"  // LITE, STANDARD, or UNLIMITED
}

Creating a client automatically provisions an isolated Snipara project with the slug format: {workspace_slug}-{client_name}.

Get Client

GET /api/integrator/clients/:clientId

Update Client

PATCH /api/integrator/clients/:clientId
{
  "name": "New Name",  // optional
  "email": "new@email.com",  // optional
  "bundle": "UNLIMITED",  // optional
  "is_active": false  // optional, deactivate client
}

Delete Client

DELETE /api/integrator/clients/:clientId

Warning: Permanent Deletion

Deleting a client permanently removes their project and all associated data. This action cannot be undone.

Client API Keys

Client API keys use the snipara_ic_ prefix to distinguish them from regular API keys. These keys grant access only to the client's project.

List API Keys

GET /api/integrator/clients/:clientId/api-keys

Create API Key

POST /api/integrator/clients/:clientId/api-keys
{
  "name": "Production Key",
  "expires_in_days": 365  // optional, null for no expiration
}

Response

{
  "success": true,
  "data": {
    "id": "key_abc123",
    "name": "Production Key",
    "key": "snipara_ic_a1b2c3d4...",  // ONLY shown once!
    "keyPrefix": "snipara_ic_a1b2",
    "expiresAt": "2027-02-19T00:00:00Z"
  }
}

Save the API Key

The full API key is only returned once during creation. Store it securely and provide it to your client.

Revoke API Key

DELETE /api/integrator/clients/:clientId/api-keys/:keyId

Webhooks

Configure a webhook URL in your workspace to receive real-time notifications about client lifecycle events.

Events

EventTrigger
client.createdNew client added to workspace
client.updatedClient details changed (name, email, bundle, status)
client.deletedClient removed from workspace
api_key.createdNew API key generated for a client
api_key.revokedAPI key revoked
Swarm & Task Events
task.createdNew task created in swarm
task.claimedAgent claimed a task
task.completedAgent completed a task successfully
task.failedTask execution failed
task.blockedTask blocked by dependency or issue
task.timeoutTask exceeded deadline — emitted automatically by the platform watchdog (see below)
htask.completedHierarchical task (N3) completed with evidence
htask.blockedHierarchical task blocked with propagation
htask.closure_readyParent task ready to close (all children done)

Payload Format

{
  "event": "client.created",
  "timestamp": "2026-02-19T15:30:00Z",
  "workspace_id": "ws_abc123",
  "data": {
    "client_id": "client_456",
    "name": "Client A",
    "email": "admin@clienta.com",
    "bundle": "STANDARD",
    "project_id": "proj_789",
    "project_slug": "acme-client-a"
  }
}

Task Event Payload

{
  "event_id": "evt_abc123",
  "event_type": "task.completed",
  "workspace_id": "ws_abc123",
  "created_at": "2026-03-27T14:30:00Z",
  "data": {
    "task_id": "task_xyz789",
    "swarm_id": "swarm_456",
    "agent_id": "mike",
    "status": "COMPLETED",
    "result": { "output": "..." }
  }
}

Task Watchdog — Automatic Timeout Detection

Snipara runs a platform-level watchdog that automatically monitors all swarm tasks and hierarchical tasks across every integrator workspace. You do not need to configure anything — timeouts are emitted as task.timeout webhooks to your endpoint.

ScenarioTriggerreason field
Task claimed but never completedclaimedAt older than swarm taskTimeout (default 5 min)execution_timeout
Task assigned but agent never claimed itcreatedAt older than swarm claimTimeout (default 10 min)never_claimed
Task created with no agent assignedcreatedAt older than swarm claimTimeoutunclaimed
Hierarchical task stalledNo updatedAt change for 24 hours while IN_PROGRESShtask_stalled

Timeouts are per-swarm. Configure them via rlm_swarm_update with taskTimeout and claimTimeout (in seconds). The watchdog scans every 2 minutes.

Task Timeout Payload

{
  "event_id": "evt_abc123",
  "event_type": "task.timeout",
  "workspace_id": "ws_abc123",
  "created_at": "2026-03-27T17:00:00Z",
  "data": {
    "task_id": "task_xyz789",
    "swarm_id": "swarm_456",
    "agent_id": "mike",
    "reason": "execution_timeout",
    "stalled_for_seconds": 720
  }
}

Use the reason field to differentiate scenarios in your handler — for example, re-dispatch on execution_timeout, alert on never_claimed, or escalate on htask_stalled.

Signature Verification

If you configure a webhook secret, all deliveries include an X-Snipara-Signature header for verification:

X-Snipara-Signature: sha256=abc123...

Verify using HMAC-SHA256:

import crypto from "crypto";
function verifyWebhook(payload: string, signature: string, secret: string): boolean {
  const expected = "sha256=" + crypto.createHmac("sha256", secret).update(payload).digest("hex");
  return crypto.timingSafeEqual(Buffer.from(signature), Buffer.from(expected));
}

Webhook Event Log

Inspect delivery history and retry failed events via the event log endpoints.

List Delivery Events

GET /v1/integrator/webhook-events
ParameterTypeDescription
limitintegerNumber of results to return (default 20)
offsetintegerPagination offset
statusstringFilter by delivery status: pending, delivered, failed
event_typestringFilter by event type (e.g. task.completed)

Retry a Failed Delivery

POST /v1/integrator/webhook-events/:eventId/retry

Re-queues the specified event for delivery. Returns the updated event record with the new delivery attempt.

Send a Test Event

POST /v1/integrator/webhook-test

Sends a test.ping event to your configured webhook URL. Useful for verifying endpoint reachability and signature verification without waiting for a real event.

Bundle Limit Enforcement

When a client exceeds their bundle limits, the MCP API returns a 429 error:

{
  "success": false,
  "error": {
    "code": "BUNDLE_LIMIT_EXCEEDED",
    "message": "Monthly query limit exceeded",
    "limit": 500,
    "current": 201,
    "reset_at": "2026-03-01T00:00:00Z"
  }
}

Enforced Limits

LimitEnforcement Point
Queries/monthEvery MCP tool call
Memoriesrlm_remember tool
Swarmsrlm_swarm_create tool
Agents/swarmrlm_swarm_join tool
DocumentsDocument upload endpoints
StorageFile upload size validation

Client API Key Usage

Once you provide a client with their snipara_ic_* API key, they can use it with any MCP-compatible client.

Claude Code Configuration

// .mcp.json
{
  "mcpServers": {
    "snipara": {
      "type": "http",
      "url": "https://api.snipara.com/mcp/{project_slug}",
      "headers": {
        "X-API-Key": "snipara_ic_..."
      }
    }
  }
}

The project_slug is automatically set when you create the client (format: {workspace_slug}-{client_name}).

Error Responses

StatusCodeDescription
400BAD_REQUESTInvalid request body or parameters
401UNAUTHORIZEDMissing or invalid authentication
403FORBIDDENNot an approved integrator
404NOT_FOUNDWorkspace, client, or key not found
409CONFLICTDuplicate email, external_id, or slug
429CLIENT_LIMIT_EXCEEDEDTier client limit reached
500INTERNAL_ERRORServer error

Next Steps