API Reference
Complete API endpoint documentation.
Base URL
https://api.smole.techInteractive Docs: Explore and test all endpoints directly in the Swagger API Reference.
Authentication
Include your API key in the X-API-Key header:
X-API-Key: ak_your_api_keySchema Endpoints
Manage your extraction schemas. See Schemas for examples of creating and using schemas.
/api/schemasCreate a new schema manually with a JSON Schema definition
/api/schemas/generateGenerate a schema using AI from field definitions (async)
/api/schemasList all your schemas
/api/schemas/:idGet a specific schema
/api/schemas/:idUpdate a schema
/api/schemas/:idDelete a schema
Workflow Endpoints
A workflow is a reusable way to process documents: it references one schema and adds its own preparation settings. Workflows belong to a workspace; get your workspace ID from GET /v1/workspaces. Paths below start with /v1/workspaces/:workspaceId.
/workflowsCreate a workflow. Returns it with version 1, which can run straight away
/workflowsList workflows, newest first. Query: limit (1–100), cursor (the previous page's nextCursor), archived
/workflows/:workflowIdGet a workflow
/workflows/:workflowIdSave a workflow. Body: { expectedRevision, input }
/workflows/:workflowId/archiveArchive a workflow. Body: { expectedRevision }
/workflows/:workflowId/versionsList a workflow's versions. Query: limit, afterVersion
/workflow-versions/:versionIdGet one workflow version
Workflow body
POST sends this object; PUT sends it as input. Every key is required and unknown keys are rejected. schemaId is a built-in schema or one of yours, and maxPages is null or 1 to 10,000.
{
"title": "Invoices (scans)",
"description": "Scanned supplier invoices",
"schemaId": "123e4567-e89b-12d3-a456-426614174000",
"definition": {
"contractVersion": 2,
"preparation": {
"forceOcr": true,
"preserveTables": true,
"preserveLinks": true,
"maxPages": null
}
}
}Saving is publishing. A save that changes the schema or the preparation settings creates the next version (latestVersion, latestVersionId); a new title or description does not. Each save, and archiving an active workflow, increases revision, so send the revision you last read as expectedRevision. Versions are immutable, and a run keeps the version it started with, even if the workflow is edited or archived while it runs.
Webhook Endpoints
Webhooks send a signed event to your endpoint each time a run of a workflow finishes. See Webhooks for events, signatures and retries. Paths below start with /v1/workspaces/:workspaceId.
/integrations/capabilitiesThe integration kinds you can set up, for example { "kinds": ["webhook"] }
/workflows/:workflowId/bindingsList a workflow's webhooks (at most 5)
/workflows/:workflowId/bindingsAdd a webhook. Body: { kind: "webhook", name, config: { url, events, includeResult } }. Returns { binding, secret }; the secret is never returned again
/bindings/:bindingIdGet a webhook. config.secretHint shows the secret's last characters
/bindings/:bindingIdChange a webhook. Body: { expectedRevision, input } with the full input
/bindings/:bindingIdDelete a webhook and cancel its queued deliveries
/bindings/:bindingId/pausePause sending. Events of finished runs wait for up to 7 days
/bindings/:bindingId/resumeResume sending and clear the failure count
/bindings/:bindingId/testQueue a free ping event
/bindings/:bindingId/rotate-secretReturns { binding, secret } with a new secret, once. The old one keeps working for 24 hours
/bindings/:bindingId/deliveriesDeliveries, newest first. Query: state (failed lists the dead letters), limit (1–100), cursor
/deliveries/:deliveryId/redeliverSend a delivered or failed event again, with the same ID and body. It never processes the document again
Pipeline Endpoints
Process documents through the extraction pipeline. See Configuration for all available parameters.
/api/pipeline/fileUpload a file and extract data using a schema or a workflow
/api/pipeline/urlProcess a document from a URL using a schema or a workflow
/api/pipeline/base64Process a base64-encoded document using a schema or a workflow
/api/pipelineList your pipeline jobs, newest first. Add ?workflowId= for one workflow's runs
/api/pipeline/:idGet pipeline job status and result
Documents and billing
Each submitted file is one document, whatever its page count, and uses 1 document unit of your plan. Conversion, OCR and extraction in one pipeline count together. Usage is reserved while a job runs, counted once when it succeeds and released if it fails or is cancelled. After a client timeout, check the existing job before submitting again to avoid duplicate work.
processingMode is optional and accepted for compatibility: both values, normal and fast, are processed the same way at the same price. processingQuoteId is optional and no longer needed. GET /api/users/me/usage reports document counts, allowance usage and pending reservations.
Run a workflow
Send exactly one of schemaId or workflowId. A workflow run uses the workflow's latest version, and that version supplies the schema and the preparation settings. The Idempotency-Key header works as for any run.
curl -X POST https://api.smole.tech/api/pipeline/file \
-H "X-API-Key: ak_your_api_key" \
-F "file=@invoice.pdf" \
-F "workflowId=your_workflow_id"
# The workflow's runs, newest first
curl "https://api.smole.tech/api/pipeline?workflowId=your_workflow_id" \
-H "X-API-Key: ak_your_api_key"Processing options cannot be sent with workflowId: the file route rejects quality, extractImages, preserveLinks, preserveTables, maxPages, ocrEnabled, ocrForce and ocrLanguages, and the URL and base64 routes reject conversionOptions and extractionChunking, each with 400 PIPELINE_VALIDATION_ERROR. The list filter returns an empty list for an unknown workflow and cannot be combined with ids.
A workflow run is a normal pipeline job and is billed like one: it uses 1 document unit, and failed runs, including RESULT_SCHEMA_INVALID, and cancelled runs are not charged: their reservation is released. Creating, editing, viewing and exporting workflows is free.
API Key Scopes
Workflow and webhook routes need a file key created for the workspace in Account → API keys, with the scopes the request needs. Processing keys work on the /api routes only.
User Endpoints
/api/users/me/usageGet current usage statistics
Response Format
Pipeline job response:
{
"id": "550e8400-e29b-41d4-a716-446655440000",
"status": "completed",
"processingMode": "normal",
"schemaId": "123e4567-e89b-12d3-a456-426614174000",
"schemaVersion": 3,
"workflowId": "9b2f6a1e-4c1d-4f7a-9e3b-2d5c8a7f1e04",
"workflowVersionId": "0c8e4d2a-7b5f-4e19-8a63-1f9d2c4b6e57",
"workflowVersion": 2,
"steps": [
{ "name": "conversion", "status": "completed" },
{ "name": "extraction", "status": "completed" }
],
"result": {
"invoiceNumber": "INV-12345",
"total": 150.00,
"date": "2024-01-15",
"purchaseOrder": null
},
"totalCostCents": 5,
"createdAt": "2024-01-15T10:00:00Z",
"completedAt": "2024-01-15T10:00:15Z"
}Fields that couldn't be found in the document are returned as null. See Missing Data and Null Values for details.
schemaVersion is the schema version the run used. workflowId, workflowVersionId and workflowVersion identify the workflow version a run pinned, and are null for runs with a schemaId. Items of GET /api/pipeline carry these fields too. A failed run, from GET /api/pipeline/:id or the list, also has error, errorCode, errorStage (conversion or extraction) and errorRetryable.
Error Codes
Errors from the /api route handlers use the first body below, sometimes with details. An unknown, disabled or expired API key, or a missing sign-in, returns 401 with only { message }. The /v1 workflow routes, and permission errors on every route, /api included, use the second body, as does 401 INVALID_API_KEY for a key that is not bound to the workspace:
{ "error": "WORKFLOW_ARCHIVED", "message": "This workflow is archived and cannot run" }
{
"code": "WORKFLOW_REVISION_CONFLICT",
"message": "This workflow changed. Reload it before saving.",
"retryAction": "change_input",
"requestId": "…"
}A key without the scope a route needs gets 403 PERMISSION_DENIED in the second body.
WORKFLOW_NOT_FOUND404The workflow does not exist in this workspace. A run also returns it for a workflow you cannot use.
WORKFLOW_ARCHIVED409The workflow is archived. It can no longer be edited or run.
WORKFLOW_REVISION_CONFLICT409expectedRevision is not the workflow's current revision. Reload it and save again.
INVALID_WORKFLOW400The workflow body is invalid: a missing or unknown key, an empty title, or maxPages outside 1 to 10,000.
SCHEMA_NOT_FOUND404The schema does not exist, or it is neither a built-in schema nor one of yours.
SCHEMA_NOT_READY409The schema is not ready (still generating, or generation failed): saving a workflow with it, or starting a run with its schemaId or with a workflow that uses it.
SCHEMA_IN_USE409DELETE /api/schemas/:id while an active workflow uses the schema. Archive the workflow first.
PIPELINE_VALIDATION_ERROR400Both or neither of schemaId and workflowId, processing options sent with workflowId, or ids combined with workflowId.
WORKFLOW_VERSION_NOT_FOUND404The workflow version does not exist in this workspace.
INVALID_REQUEST400A workflow request is malformed: a PUT body that is not exactly { expectedRevision, input }, an archive body that is not exactly { expectedRevision }, or an invalid query.
INVALID_REVISION400expectedRevision is not a positive integer.
CONTRACT_VERSION_UNSUPPORTED400definition.contractVersion is not 2.
INVALID_CURSOR400The list cursor was not returned by this list.
DESTINATION_URL_NOT_ALLOWED400The webhook URL is not public HTTPS on port 443, has credentials, or resolves to a local or private address.
INVALID_BINDING400The webhook body is invalid: a missing or unknown key, an empty name, or no events.
BINDING_NOT_FOUND404The webhook does not exist in this workspace.
DELIVERY_NOT_FOUND404The delivery does not exist. Finished deliveries are kept for 30 days.
BINDING_LIMIT_REACHED409A limit is reached: the workflow already has 5 outputs (webhooks and Google Sheets together) or 5 sources, the Google Sheet already serves 10 workflows, or the workspace already holds 1,000 sources and outputs.
BINDING_REVISION_CONFLICT409expectedRevision is not the webhook's current revision, or another rotation won. Reload it and try again.
BINDING_TEST_IN_PROGRESS409A test ping of this webhook is still on its way.
DELIVERY_NOT_REDELIVERABLE409The delivery is still queued or being sent. Only delivered or failed deliveries can be sent again.
INTEGRATION_DISABLED503This kind of integration is not available for this workspace.