API Reference

API Reference

Compact endpoint reference for Klarefi API v1

API base URL

Examples use https://www.klarefi.com. The direct regional Convex HTTP URL shown in Settings → Developer is also supported.

Endpoints

MethodPathScopePurpose
GET/api/v1/healthNoneService health check
GET/api/v1/mecases:readIdentify the authenticated org
POST/api/v1/sessionsintake:sessions:createCreate a hosted intake session
POST/api/v1/sessions/\{sessionId\}/handoffintake:sessions:createComplete customer-side handoff
POST/api/v1/processcases:processQueue a document for processing
GET/api/v1/connectorsconnectors:read/writeList configured connectors
POST/api/v1/connectorsconnectors:writeCreate or update a connector
POST/api/v1/connectors/importconnectors:writeImport an OpenAPI connector
GET/api/v1/connectors/\{connectorKey\}connectors:read/writeRead a configured connector
DELETE/api/v1/connectors/\{connectorKey\}connectors:writeDelete a configured connector
GET/api/v1/cases/\{caseId\}cases:readRead current case state
GET/api/v1/cases/\{caseId\}/eventscases:readPoll intake events
GET/api/v1/cases/\{caseId\}/packagecases:readRead the decision-ready package
GET/api/v1/cases/\{caseId\}/workspacecases:readRead the cited operator workspace
POST/api/v1/cases/\{caseId\}/commandscases:reviewSubmit an intake-review command
GET/api/v1/cases/\{caseId\}/commands/\{commandId\}cases:readPoll an intake-review command
GET/api/v1/operator/queuecases:reviewList the bounded operator queue
GET/api/v1/workflowsworkflows:readList workflow declarations
POST/api/v1/workflowsworkflows:writeSave a workflow draft
DELETE/api/v1/documents/\{docId\}privacy:eraseErase a document and derived data
POST/api/v1/webhooks/testwebhooks:testSend a signed test delivery
POST/api/v1/webhooks/deliveries/\{deliveryId\}/ackwebhooks:acknowledgeAcknowledge webhook handoff

GET /api/v1/health

{
  "status": "ok"
}

GET /api/v1/me

{
  "org_id": "org_abc123",
  "environment": "test"
}

POST /api/v1/sessions

{
  "case_type_id": "motor_claim",
  "idempotency_key": "session_claim_12345",
  "external_case_id": "claim_12345",
  "ttl_hours": 168,
  "locale": "nl"
}
{
  "session_id": "550e8400-e29b-41d4-a716-446655440000",
  "signed_url": "https://app.klarefi.com/s/550e8400...?token=...",
  "access_token": "1751879000.9f2c4e...",
  "access_token_expires_at": "2026-01-22T10:30:00.000Z",
  "expires_at": "2026-01-22T10:30:00.000Z",
  "agent": {
    "api_base": "https://your-deployment.convex.site/api/v1",
    "manifest_url": "https://your-deployment.convex.site/api/v1/sessions/550e8400-e29b-41d4-a716-446655440000/manifest",
    "access_token": "1751879000.9f2c4e..."
  },
  "snippet": "<script>window.location.href=\"https://app.klarefi.com/s/...\";</script>",
  "idempotent_replay": false
}

snippet is a redirect helper that sends the browser to signed_url. For on-site embedding, use the embed script.

Errors: 400 invalid_json, missing_case_type_id, idempotency, external ID, or prefill validation errors; 401 invalid_api_key; 403 forbidden; 402 billing errors; 428 account preconditions; 429 rate_limit_exceeded; 500 internal_error.

POST /api/v1/sessions/{sessionId}/handoff

Required scope: intake:sessions:create.

The body is optional. To ask Klarefi to send the applicant a continue link:

{
  "notify": { "email": "applicant@example.com" }
}
{
  "session_id": "550e8400-e29b-41d4-a716-446655440000",
  "signed_url": "https://app.klarefi.com/s/550e8400...?token=...",
  "access_token": "1751879000.9f2c4e...",
  "access_token_expires_at": "2026-01-22T10:30:00.000Z",
  "expires_at": "2026-01-22T10:30:00.000Z",
  "customer_completed_at": "2026-01-15T10:30:00.000Z",
  "already_marked": false,
  "notification": { "requested": true, "sent": true }
}

notification is omitted when notify is absent. A failed email does not fail the handoff; it returns sent: false with email_not_configured or send_failed.

Errors: 400 validation_error; 401 invalid_api_key; 403 forbidden; 404 session_not_found; 409 session_terminal; 429 rate_limit_exceeded; 500 internal_error.

POST /api/v1/process

Required scope: cases:process.

{
  "document_url": "https://files.example.com/claim.pdf",
  "case_type_id": "motor_claim",
  "idempotency_key": "process_claim_12345",
  "external_case_id": "claim_12345",
  "external_applicant_id": "applicant_789",
  "external_customer_id": "customer_456",
  "trace_id": "trace_claim_12345"
}
{
  "case_id": "case_abc123",
  "doc_id": "doc_def456",
  "job_id": "job_ghi789",
  "status": "queued",
  "idempotent_replay": false
}

Returns 201 for new work and 200 for an idempotent replay.

Errors: 400 invalid_json, missing_document_url, invalid_document_url, missing_case_type_id, per_request_webhook_url_not_supported, integration identity, idempotency, or external ID errors; 401 invalid_api_key; 403 forbidden; 402 billing errors; 428 account or self-serve webhook preconditions; 429 rate_limit_exceeded; 500 internal_error.

GET /api/v1/connectors

Required scope: connectors:read or connectors:write.

{
  "connectors": [
    {
      "connector_key": "claims_api",
      "label": "Claims API",
      "connector_type": "http_api",
      "transport": {
        "base_url": "https://claims.example.com",
        "timeout_ms": 10000,
        "default_headers": [],
        "auth": {
          "mode": "bearer_token",
          "has_secret": true,
          "has_username": false,
          "has_password": false
        }
      },
      "functions": []
    }
  ],
  "environment": "test"
}

Stored transport secrets are never returned. Errors: 401 invalid_api_key, 403 forbidden, 429 rate_limit_exceeded, 500 internal_error.

POST /api/v1/connectors

Required scope: connectors:write.

{
  "connector_key": "claims_api",
  "label": "Claims API",
  "connector_type": "http_api",
  "transport": {
    "base_url": "https://claims.example.com",
    "timeout_ms": 10000,
    "auth": { "mode": "bearer_token", "secret": "secret-value" }
  },
  "functions": [
    {
      "function_key": "lookup_claim",
      "label": "Lookup claim",
      "usage": "verify_fact",
      "request": { "method": "GET", "path": "/claims/{{claim_id}}" },
      "input_parameters": [
        { "name": "claim_id", "type": "text", "required": true }
      ],
      "sample_input": { "claim_id": "CLM-123" },
      "success_criteria": { "status_codes": [200] }
    }
  ]
}
{
  "connector_key": "claims_api",
  "created": true,
  "environment": "test"
}

Returns 201 when created and 200 when updated. The connector is active immediately. Errors: 400 invalid_json or invalid_connector_payload; 401 invalid_api_key; 403 forbidden; 429 rate_limit_exceeded; 500 internal_error.

POST /api/v1/connectors/import

Required scope: connectors:write.

Provide openapi_url, openapi_json, or an inline openapi object. OpenAPI documents must be JSON; YAML imports are rejected.

{
  "connector_key": "claims_api",
  "label": "Claims API",
  "openapi_url": "https://claims.example.com/openapi.json",
  "auth": { "mode": "bearer_token", "secret": "secret-value" }
}
{
  "connector_key": "claims_api",
  "created": true,
  "environment": "test",
  "functions_imported": 4
}

Returns 201 when created and 200 when updated. Errors: 400 invalid_json, missing_connector_key, openapi_fetch_failed, missing_openapi_spec, openapi_yaml_not_supported, invalid_openapi_spec, or invalid_openapi_connector; 401 invalid_api_key; 403 forbidden; 429 rate_limit_exceeded; 500 internal_error.

GET /api/v1/connectors/{connectorKey}

Required scope: connectors:read or connectors:write.

{
  "connector": {
    "connector_key": "claims_api",
    "label": "Claims API",
    "connector_type": "http_api",
    "transport": {
      "base_url": "https://claims.example.com",
      "timeout_ms": 10000,
      "default_headers": [],
      "auth": { "mode": "bearer_token", "has_secret": true }
    },
    "functions": []
  },
  "environment": "test"
}

Errors: 401 invalid_api_key, 403 forbidden, 404 not_found, 429 rate_limit_exceeded, 500 internal_error.

DELETE /api/v1/connectors/{connectorKey}

Required scope: connectors:write.

{
  "connector_key": "claims_api",
  "deleted": true,
  "environment": "test"
}

Errors: 401 invalid_api_key, 403 forbidden, 404 not_found, 429 rate_limit_exceeded, 500 internal_error.

GET /api/v1/cases/{caseId}

The case response is the current operator workspace projection. Its runtime_status is one of processing, intake_in_progress, gate_ready, gate_evaluating, ready_for_review, or complete. Unknown fields are allowed. This abbreviated response shows the top-level nesting used by the projection.

{
  "case_id": "case_abc123",
  "case_type_id": "motor_claim",
  "workflow_id": "motor_claim_intake",
  "workflow_version": "3",
  "operating_mode": "system_of_action",
  "runtime_status": "ready_for_review",
  "workspace": {
    "facts": [
      {
        "fact_id": "incident_date",
        "fact_label": "Incident date",
        "status": "resolved",
        "value": "2023-02-03",
        "reason_codes": [],
        "provenance": [
          {
            "kind": "document_span",
            "document_id": "doc_def456",
            "page_index": 0,
            "quote": "3 februari 2023"
          }
        ],
        "verification_metadata": [],
        "evidence": [
          {
            "evidence_id": "ev_001",
            "quote": "3 februari 2023",
            "location": { "char_start": 142, "char_end": 158 },
            "doc_id": "doc_def456",
            "page_index": 0
          }
        ]
      }
    ],
    "documents": [
      {
        "doc_id": "doc_def456",
        "status": "processed",
        "mime_type": "application/pdf"
      }
    ]
  },
  "updated_at": "2026-01-15T10:30:00.000Z"
}

POST /api/v1/cases/\{caseId\}/commands requires an idempotency key in either the JSON idempotency_key field or the Idempotency-Key header. It accepts only intake-review commands and cannot complete or reopen a case. Workflow writes always save drafts; publishing remains human-controlled.

GET /api/v1/cases/{caseId}/events

Query parameters: after_cursor, default 0; limit, default 100, maximum 500.

{
  "case_id": "case_abc123",
  "events": [
    {
      "event_id": "evt_001",
      "event_type": "document.processed",
      "cursor": 1,
      "created_at": "2026-01-15T10:30:00Z"
    }
  ],
  "next_cursor": 1,
  "has_more": false
}

GET /api/v1/cases/{caseId}/package

The package response is workflow-shaped and includes case_file_url.

{
  "case_id": "case_abc123",
  "case_file_url": "https://app.klarefi.com/case-file/case_abc123?token=..."
}

DELETE /api/v1/documents/{docId}

Returns 200 when complete or 202 when another erasure batch remains.

{
  "erasure_receipt": {
    "doc_id": "doc_def456",
    "audit_id": "audit_001",
    "completed": true,
    "deleted_evidence": 5,
    "deleted_candidates": 3,
    "deleted_document": true,
    "timestamp": "2026-01-15T10:30:00.000Z"
  }
}

POST /api/v1/webhooks/test

{
  "endpoint_url": "https://your-app.example.com/webhooks/klarefi",
  "signing_secret": "whsec_your_signing_secret"
}
{
  "success": true,
  "status_code": 200
}

POST /api/v1/webhooks/deliveries/{deliveryId}/ack

{
  "acknowledgement_id": "ack_claim_12345"
}
{
  "acknowledged": true,
  "already_acknowledged": false,
  "delivery_id": "whd_123"
}

On this page