Sada Files

Developer docs

  1. Developers

Jobs and pipelines

Every run is a job. Short ones can wait in the request; long ones run in the background while you poll or get a callback.

Sync or async

RouteSuccessUse it for
POST /v1/tools/:slug201 with the file; 202 with the job after 60 sSmall files and quick tools
POST /v1/tools/:slug/jobs201 with the job at onceLarge files, OCR, video, anything slow
Start a job
curl -X POST "https://api.sadafiles.com/v1/tools/pdf-to-word/jobs" \
  -H "X-API-Key: $SADAFILES_API_KEY" \
  -F "files[]=@report.pdf"

Job lifecycle

A job moves from queued to running and ends as done, failed, cancelled or expired. Ids are UUIDs. Inputs, outputs and the per-job key are purged by expiresAt, at most 24 hours later.

GET /v1/jobs/:id
{
  "id": "de01bc4a-0686-400b-a594-20f031191629",
  "status": "running",
  "tool": "pdf-to-word",
  "steps": [
    "pdf-to-word"
  ],
  "runtime": "server",
  "progress": {
    "percent": 40,
    "stepIndex": 0,
    "stepCount": 1
  },
  "inputCount": 1,
  "inputBytes": 182044,
  "queuedAt": "2026-11-01T16:31:37.714Z",
  "expiresAt": "2026-11-02T16:31:37.708Z"
}

Job endpoints

RouteScopeDoes
GET /v1/jobs/:idjobs:readStatus and progress
GET /v1/jobs/:id/resultjobs:readDownload the result, as often as you like until it expires
POST /v1/jobs/:id/continuejobs:write, tools:runRun more steps on the output without uploading again
POST /v1/jobs/:id/canceljobs:writeStop a queued or running job
DELETE /v1/jobs/:idjobs:writePurge inputs, outputs and the key now (204)

Pipelines

Send up to 32 steps in the steps field. Each step's output feeds the next, and the whole chain is checked before it starts; a bad link returns PIPELINE_INCOMPATIBLE. Add ?async=1 to get the job back straight away (202).

Resize, then compress
curl -X POST "https://api.sadafiles.com/v1/pipeline" \
  -H "X-API-Key: $SADAFILES_API_KEY" \
  -F "files[]=@photo.jpg" \
  -F 'steps=[{"tool":"resize-image","options":{"width":1200}},{"tool":"compress-image","options":{"quality":80}}]' \
  -o result.jpg

Weigh up what each tool takes and returns on its endpoint page. The optional output field is JSON like steps, so quote the value in a form field: -F 'output="zip"'. It takes single, zip or json-urls.

Batches

POST /v1/batches takes up to 500 files plus a tool (with options) or steps, and creates one job per file. GET /v1/batches/:id reports progress and GET /v1/batches/:id/result returns a ZIP of everything that finished.

Compress a folder
curl -X POST "https://api.sadafiles.com/v1/batches" \
  -H "X-API-Key: $SADAFILES_API_KEY" \
  -F "files[]=@one.jpg" \
  -F "files[]=@two.jpg" \
  -F "tool=compress-image"

Safe retries

Send an Idempotency-Key header on tool and pipeline runs. If a network error makes you retry, the same key returns the existing job instead of creating a second one.

Live progress

Polling works everywhere. For live updates, connect with Socket.IO to the /jobs namespace, passing your key as auth.apiKey, then emit subscribe with { id }. You receive job.progress, job.completed, job.failed and job.deleted, with metadata only. The key needs jobs:read.

What's next?