{"openapi":"3.1.0","info":{"title":"Zegi API","version":"v1","description":"Zegi — UAE-first OCR & document intelligence. Extract text and structured data from images and PDFs, synchronously or asynchronously, with usage metering, webhooks and predictable errors. Authenticate with an API key as `Authorization: Bearer <key>`.","contact":{"name":"Zegi Support","url":"https://zegi.ae/support"}},"servers":[{"url":"https://zegi.ae/api/v1","description":"Production v1"}],"security":[{"bearerAuth":[]},{"apiKeyHeader":[]}],"tags":[{"name":"OCR","description":"Extract text and structured data."},{"name":"Documents","description":"Stored documents and their results (opt-in persistence)."},{"name":"Compression","description":"Compress and convert images and PDFs."},{"name":"Document Tools","description":"Merge, split, and convert PDF documents."},{"name":"Exports","description":"Export OCR text/structured data to files."},{"name":"Jobs","description":"Asynchronous OCR job status and results."},{"name":"Account","description":"Account, plan, usage and limits."},{"name":"Webhooks","description":"Register endpoints to receive signed events."},{"name":"System","description":"Health and capabilities (public)."}],"paths":{"/health":{"get":{"tags":["System"],"summary":"Service health","security":[],"responses":{"200":{"description":"Healthy","content":{"application/json":{"schema":{"type":"object","properties":{"status":{"type":"string","example":"healthy"}}}}}}}}},"/capabilities":{"get":{"tags":["System"],"summary":"Supported formats and capabilities","security":[],"responses":{"200":{"description":"Capabilities"}}}},"/account":{"get":{"tags":["Account"],"summary":"Account, plan, usage and limits","description":"Requires scope `usage:read`.","responses":{"200":{"description":"Account details","content":{"application/json":{"schema":{"type":"object","required":["success","request_id","api_version","data"],"properties":{"success":{"type":"boolean","enum":[true]},"request_id":{"type":"string","example":"req_9f2c1a7b3d4e5f60"},"api_version":{"type":"string","enum":["v1"]},"data":{"$ref":"#/components/schemas/Account"}}}}}},"401":{"description":"MISSING_API_KEY · INVALID_API_KEY","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"MISSING_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"MISSING_API_KEY","message":"An API key is required. Provide it as 'Authorization: Bearer <key>'."}}},"INVALID_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INVALID_API_KEY","message":"The API key is invalid."}}}}}}},"403":{"description":"INSUFFICIENT_SCOPE","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INSUFFICIENT_SCOPE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INSUFFICIENT_SCOPE","message":"This API key lacks the scope required for this operation."}}}}}}},"429":{"description":"RATE_LIMITED","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"RATE_LIMITED":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"RATE_LIMITED","message":"Too many requests. Please slow down and retry later."}}}}}}}}}},"/ocr":{"post":{"tags":["OCR"],"summary":"Run OCR (synchronous, or asynchronous with ?async=true)","description":"Requires scope `ocr:process` and API access enabled. Send multipart/form-data with `file` (or `files`). Synchronous by default; pass `?async=true` to enqueue a job and receive 202 with a `job_id`. Supports `Idempotency-Key` for async submissions and `?includeLayout=true` for per-line bounding boxes.","parameters":[{"name":"async","in":"query","schema":{"type":"boolean"},"description":"Enqueue an async job and return 202."},{"name":"store","in":"query","schema":{"type":"boolean"},"description":"Persist the document + result for later retrieval (requires scope documents:write). Returns document_id + result_url."},{"name":"includeLayout","in":"query","schema":{"type":"boolean"},"description":"Include per-line bounding boxes."},{"name":"Idempotency-Key","in":"header","schema":{"type":"string"},"description":"Dedupe async submissions."}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"type":"object","properties":{"file":{"type":"string","format":"binary"},"files":{"type":"array","items":{"type":"string","format":"binary"}}}}}}},"responses":{"200":{"description":"Synchronous OCR result","content":{"application/json":{"schema":{"type":"object","required":["success","request_id","api_version","data"],"properties":{"success":{"type":"boolean","enum":[true]},"request_id":{"type":"string","example":"req_9f2c1a7b3d4e5f60"},"api_version":{"type":"string","enum":["v1"]},"data":{"type":"object","properties":{"files":{"type":"array","items":{"$ref":"#/components/schemas/OcrFileResult"}}}}}}}}},"202":{"description":"Async job accepted","content":{"application/json":{"schema":{"type":"object","required":["success","request_id","api_version","data"],"properties":{"success":{"type":"boolean","enum":[true]},"request_id":{"type":"string","example":"req_9f2c1a7b3d4e5f60"},"api_version":{"type":"string","enum":["v1"]},"data":{"$ref":"#/components/schemas/JobAccepted"}}}}}},"401":{"description":"MISSING_API_KEY · INVALID_API_KEY","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"MISSING_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"MISSING_API_KEY","message":"An API key is required. Provide it as 'Authorization: Bearer <key>'."}}},"INVALID_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INVALID_API_KEY","message":"The API key is invalid."}}}}}}},"403":{"description":"INSUFFICIENT_SCOPE · API_ACCESS_NOT_ENABLED","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INSUFFICIENT_SCOPE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INSUFFICIENT_SCOPE","message":"This API key lacks the scope required for this operation."}}},"API_ACCESS_NOT_ENABLED":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"API_ACCESS_NOT_ENABLED","message":"API processing is not enabled for this account."}}}}}}},"413":{"description":"FILE_TOO_LARGE","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"FILE_TOO_LARGE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"FILE_TOO_LARGE","message":"The uploaded file exceeds the maximum allowed size."}}}}}}},"415":{"description":"UNSUPPORTED_FILE_TYPE","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"UNSUPPORTED_FILE_TYPE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"UNSUPPORTED_FILE_TYPE","message":"This file type is not supported."}}}}}}},"429":{"description":"USAGE_LIMIT_EXCEEDED · RATE_LIMITED","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"USAGE_LIMIT_EXCEEDED":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"USAGE_LIMIT_EXCEEDED","message":"Your page allowance has been reached."}}},"RATE_LIMITED":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"RATE_LIMITED","message":"Too many requests. Please slow down and retry later."}}}}}}},"500":{"description":"OCR_FAILED","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"OCR_FAILED":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"OCR_FAILED","message":"OCR processing failed. Please try again."}}}}}}},"503":{"description":"API_DISABLED","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"API_DISABLED":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"API_DISABLED","message":"The API is temporarily unavailable."}}}}}}}}}},"/compress":{"post":{"tags":["Compression"],"summary":"Compress or convert an image or PDF","description":"Requires scope `compression:process` and API access enabled. Send multipart/form-data with `file` and optional `op` (image|pdf|convert), `quality`, `maxDimension`, `target`, `format`. Returns the compressed file as a binary download with X-Original-Size / X-Compressed-Size headers. Requires a configured compression worker (otherwise 503).","requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"type":"object","properties":{"file":{"type":"string","format":"binary"},"op":{"type":"string","enum":["image","pdf","convert"]},"quality":{"type":"integer"},"format":{"type":"string"}}}}}},"responses":{"200":{"description":"Compressed file (binary)","content":{"application/octet-stream":{"schema":{"type":"string","format":"binary"}}}},"401":{"description":"MISSING_API_KEY · INVALID_API_KEY","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"MISSING_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"MISSING_API_KEY","message":"An API key is required. Provide it as 'Authorization: Bearer <key>'."}}},"INVALID_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INVALID_API_KEY","message":"The API key is invalid."}}}}}}},"403":{"description":"INSUFFICIENT_SCOPE · API_ACCESS_NOT_ENABLED","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INSUFFICIENT_SCOPE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INSUFFICIENT_SCOPE","message":"This API key lacks the scope required for this operation."}}},"API_ACCESS_NOT_ENABLED":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"API_ACCESS_NOT_ENABLED","message":"API processing is not enabled for this account."}}}}}}},"413":{"description":"FILE_TOO_LARGE","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"FILE_TOO_LARGE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"FILE_TOO_LARGE","message":"The uploaded file exceeds the maximum allowed size."}}}}}}},"503":{"description":"API_DISABLED · WORKER_UNAVAILABLE","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"API_DISABLED":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"API_DISABLED","message":"The API is temporarily unavailable."}}},"WORKER_UNAVAILABLE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"WORKER_UNAVAILABLE","message":"The processing service is temporarily unavailable."}}}}}}}}}},"/pdf/merge":{"post":{"tags":["Document Tools"],"summary":"Merge multiple PDFs into one","description":"Requires scope `pdf:merge` and API access enabled. Send multipart/form-data with 2–20 PDFs in `files`. Returns the merged PDF as a binary download.","requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"type":"object","required":["files"],"properties":{"files":{"type":"array","items":{"type":"string","format":"binary"}}}}}}},"responses":{"200":{"description":"Merged PDF (binary)","content":{"application/pdf":{"schema":{"type":"string","format":"binary"}}}},"400":{"description":"INVALID_REQUEST","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INVALID_REQUEST":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INVALID_REQUEST","message":"The request is invalid."}}}}}}},"401":{"description":"MISSING_API_KEY · INVALID_API_KEY","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"MISSING_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"MISSING_API_KEY","message":"An API key is required. Provide it as 'Authorization: Bearer <key>'."}}},"INVALID_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INVALID_API_KEY","message":"The API key is invalid."}}}}}}},"403":{"description":"INSUFFICIENT_SCOPE · API_ACCESS_NOT_ENABLED","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INSUFFICIENT_SCOPE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INSUFFICIENT_SCOPE","message":"This API key lacks the scope required for this operation."}}},"API_ACCESS_NOT_ENABLED":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"API_ACCESS_NOT_ENABLED","message":"API processing is not enabled for this account."}}}}}}},"413":{"description":"FILE_TOO_LARGE","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"FILE_TOO_LARGE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"FILE_TOO_LARGE","message":"The uploaded file exceeds the maximum allowed size."}}}}}}},"415":{"description":"UNSUPPORTED_FILE_TYPE","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"UNSUPPORTED_FILE_TYPE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"UNSUPPORTED_FILE_TYPE","message":"This file type is not supported."}}}}}}},"429":{"description":"USAGE_LIMIT_EXCEEDED · RATE_LIMITED","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"USAGE_LIMIT_EXCEEDED":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"USAGE_LIMIT_EXCEEDED","message":"Your page allowance has been reached."}}},"RATE_LIMITED":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"RATE_LIMITED","message":"Too many requests. Please slow down and retry later."}}}}}}},"503":{"description":"API_DISABLED","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"API_DISABLED":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"API_DISABLED","message":"The API is temporarily unavailable."}}}}}}}}}},"/pdf/split":{"post":{"tags":["Document Tools"],"summary":"Split a PDF into pages or ranges","description":"Requires scope `pdf:split` and API access enabled. Send multipart/form-data with one `file` and optional `mode` (all|ranges|odd|even) and `ranges` (e.g. `1-3,5`). Returns a single PDF when one file results, otherwise a ZIP archive.","requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"type":"object","required":["file"],"properties":{"file":{"type":"string","format":"binary"},"mode":{"type":"string","enum":["all","ranges","odd","even"]},"ranges":{"type":"string"}}}}}},"responses":{"200":{"description":"Split PDF or ZIP (binary)","content":{"application/octet-stream":{"schema":{"type":"string","format":"binary"}}}},"400":{"description":"INVALID_REQUEST","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INVALID_REQUEST":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INVALID_REQUEST","message":"The request is invalid."}}}}}}},"401":{"description":"MISSING_API_KEY · INVALID_API_KEY","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"MISSING_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"MISSING_API_KEY","message":"An API key is required. Provide it as 'Authorization: Bearer <key>'."}}},"INVALID_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INVALID_API_KEY","message":"The API key is invalid."}}}}}}},"403":{"description":"INSUFFICIENT_SCOPE · API_ACCESS_NOT_ENABLED","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INSUFFICIENT_SCOPE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INSUFFICIENT_SCOPE","message":"This API key lacks the scope required for this operation."}}},"API_ACCESS_NOT_ENABLED":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"API_ACCESS_NOT_ENABLED","message":"API processing is not enabled for this account."}}}}}}},"413":{"description":"FILE_TOO_LARGE","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"FILE_TOO_LARGE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"FILE_TOO_LARGE","message":"The uploaded file exceeds the maximum allowed size."}}}}}}},"415":{"description":"UNSUPPORTED_FILE_TYPE","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"UNSUPPORTED_FILE_TYPE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"UNSUPPORTED_FILE_TYPE","message":"This file type is not supported."}}}}}}},"429":{"description":"USAGE_LIMIT_EXCEEDED · RATE_LIMITED","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"USAGE_LIMIT_EXCEEDED":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"USAGE_LIMIT_EXCEEDED","message":"Your page allowance has been reached."}}},"RATE_LIMITED":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"RATE_LIMITED","message":"Too many requests. Please slow down and retry later."}}}}}}},"503":{"description":"API_DISABLED","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"API_DISABLED":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"API_DISABLED","message":"The API is temporarily unavailable."}}}}}}}}}},"/pdf/to-word":{"post":{"tags":["Document Tools"],"summary":"Convert a PDF to Word (.docx)","description":"Requires scope `pdf:convert` and API access enabled. Send multipart/form-data with one `file`. Digital PDFs use their native text layer; scanned or image-only PDFs are converted via OCR. Returns the .docx as a binary download.","requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"type":"object","required":["file"],"properties":{"file":{"type":"string","format":"binary"}}}}}},"responses":{"200":{"description":"Word document (binary)","content":{"application/vnd.openxmlformats-officedocument.wordprocessingml.document":{"schema":{"type":"string","format":"binary"}}}},"400":{"description":"INVALID_REQUEST","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INVALID_REQUEST":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INVALID_REQUEST","message":"The request is invalid."}}}}}}},"401":{"description":"MISSING_API_KEY · INVALID_API_KEY","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"MISSING_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"MISSING_API_KEY","message":"An API key is required. Provide it as 'Authorization: Bearer <key>'."}}},"INVALID_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INVALID_API_KEY","message":"The API key is invalid."}}}}}}},"403":{"description":"INSUFFICIENT_SCOPE · API_ACCESS_NOT_ENABLED","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INSUFFICIENT_SCOPE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INSUFFICIENT_SCOPE","message":"This API key lacks the scope required for this operation."}}},"API_ACCESS_NOT_ENABLED":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"API_ACCESS_NOT_ENABLED","message":"API processing is not enabled for this account."}}}}}}},"413":{"description":"FILE_TOO_LARGE","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"FILE_TOO_LARGE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"FILE_TOO_LARGE","message":"The uploaded file exceeds the maximum allowed size."}}}}}}},"415":{"description":"UNSUPPORTED_FILE_TYPE","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"UNSUPPORTED_FILE_TYPE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"UNSUPPORTED_FILE_TYPE","message":"This file type is not supported."}}}}}}},"422":{"description":"INVALID_DOCUMENT","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INVALID_DOCUMENT":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INVALID_DOCUMENT","message":"The document could not be processed."}}}}}}},"503":{"description":"API_DISABLED","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"API_DISABLED":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"API_DISABLED","message":"The API is temporarily unavailable."}}}}}}}}}},"/pdf/to-excel":{"post":{"tags":["Document Tools"],"summary":"Convert a PDF to Excel (.xlsx)","description":"Requires scope `pdf:convert` and API access enabled. Send multipart/form-data with one `file`. Reconstructs a multi-sheet workbook — Document View (faithful cells), Structured Data (typed fields), Applied Invoices (a real table), and Validation — from native text geometry (digital PDFs) or OCR (scanned/image-only PDFs). Optional params: `conversion_mode` (full|data|raw), `preserve_layout` (bool), `include_structured_data` (bool), `document_type` (hint). Returns the .xlsx as a binary download.","requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"type":"object","required":["file"],"properties":{"file":{"type":"string","format":"binary"},"conversion_mode":{"type":"string","enum":["full","data","raw"],"description":"full = all sheets (default); data = structured sheets only (no Document View); raw = plain per-page grid."},"preserve_layout":{"type":"boolean","description":"Include the visual Document View sheet (default true)."},"include_structured_data":{"type":"boolean","description":"Include the Structured Data + Validation sheets (default true)."},"document_type":{"type":"string","description":"Optional hint to label the document type."}}}}}},"responses":{"200":{"description":"Excel workbook (binary)","content":{"application/vnd.openxmlformats-officedocument.spreadsheetml.sheet":{"schema":{"type":"string","format":"binary"}}}},"400":{"description":"INVALID_REQUEST","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INVALID_REQUEST":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INVALID_REQUEST","message":"The request is invalid."}}}}}}},"401":{"description":"MISSING_API_KEY · INVALID_API_KEY","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"MISSING_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"MISSING_API_KEY","message":"An API key is required. Provide it as 'Authorization: Bearer <key>'."}}},"INVALID_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INVALID_API_KEY","message":"The API key is invalid."}}}}}}},"403":{"description":"INSUFFICIENT_SCOPE · API_ACCESS_NOT_ENABLED","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INSUFFICIENT_SCOPE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INSUFFICIENT_SCOPE","message":"This API key lacks the scope required for this operation."}}},"API_ACCESS_NOT_ENABLED":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"API_ACCESS_NOT_ENABLED","message":"API processing is not enabled for this account."}}}}}}},"413":{"description":"FILE_TOO_LARGE","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"FILE_TOO_LARGE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"FILE_TOO_LARGE","message":"The uploaded file exceeds the maximum allowed size."}}}}}}},"415":{"description":"UNSUPPORTED_FILE_TYPE","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"UNSUPPORTED_FILE_TYPE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"UNSUPPORTED_FILE_TYPE","message":"This file type is not supported."}}}}}}},"422":{"description":"INVALID_DOCUMENT","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INVALID_DOCUMENT":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INVALID_DOCUMENT","message":"The document could not be processed."}}}}}}},"503":{"description":"API_DISABLED","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"API_DISABLED":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"API_DISABLED","message":"The API is temporarily unavailable."}}}}}}}}}},"/pdf/searchable":{"post":{"tags":["Document Tools"],"summary":"Create a searchable PDF from an image","description":"Requires scope `pdf:searchable` and API access enabled. Send multipart/form-data with one image `file` (PNG/JPEG/WebP). Runs OCR and returns a PDF with the original image plus an invisible, searchable text layer (Arabic included). WebP falls back to a text-only searchable PDF.","requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"type":"object","required":["file"],"properties":{"file":{"type":"string","format":"binary"}}}}}},"responses":{"200":{"description":"Searchable PDF (binary)","content":{"application/pdf":{"schema":{"type":"string","format":"binary"}}}},"400":{"description":"INVALID_REQUEST","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INVALID_REQUEST":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INVALID_REQUEST","message":"The request is invalid."}}}}}}},"401":{"description":"MISSING_API_KEY · INVALID_API_KEY","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"MISSING_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"MISSING_API_KEY","message":"An API key is required. Provide it as 'Authorization: Bearer <key>'."}}},"INVALID_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INVALID_API_KEY","message":"The API key is invalid."}}}}}}},"403":{"description":"INSUFFICIENT_SCOPE · API_ACCESS_NOT_ENABLED","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INSUFFICIENT_SCOPE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INSUFFICIENT_SCOPE","message":"This API key lacks the scope required for this operation."}}},"API_ACCESS_NOT_ENABLED":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"API_ACCESS_NOT_ENABLED","message":"API processing is not enabled for this account."}}}}}}},"413":{"description":"FILE_TOO_LARGE","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"FILE_TOO_LARGE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"FILE_TOO_LARGE","message":"The uploaded file exceeds the maximum allowed size."}}}}}}},"415":{"description":"UNSUPPORTED_FILE_TYPE","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"UNSUPPORTED_FILE_TYPE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"UNSUPPORTED_FILE_TYPE","message":"This file type is not supported."}}}}}}},"422":{"description":"INVALID_DOCUMENT","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INVALID_DOCUMENT":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INVALID_DOCUMENT","message":"The document could not be processed."}}}}}}},"429":{"description":"USAGE_LIMIT_EXCEEDED · RATE_LIMITED","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"USAGE_LIMIT_EXCEEDED":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"USAGE_LIMIT_EXCEEDED","message":"Your page allowance has been reached."}}},"RATE_LIMITED":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"RATE_LIMITED","message":"Too many requests. Please slow down and retry later."}}}}}}},"503":{"description":"API_DISABLED · WORKER_UNAVAILABLE","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"API_DISABLED":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"API_DISABLED","message":"The API is temporarily unavailable."}}},"WORKER_UNAVAILABLE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"WORKER_UNAVAILABLE","message":"The processing service is temporarily unavailable."}}}}}}}}}},"/image/enhance":{"post":{"tags":["Document Tools"],"summary":"Enhance and upscale an image","description":"Requires scope `image:enhance` and API access enabled. Send multipart/form-data with one image `file` (PNG/JPEG/WebP). Improves clarity (denoise, local contrast, sharpen) and optionally upscales — in-process, open-source, no per-image AI fee. NOTE: upscaling interpolates and does not invent lost detail. Optional params: `mode` (auto|photo|document|screenshot|portrait), `scale` (1|2|4), `level` (natural|balanced|enhanced|maximum), `format` (auto|jpeg|png|webp|avif). Returns the enhanced image as a binary download.","requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"type":"object","required":["file"],"properties":{"file":{"type":"string","format":"binary"},"mode":{"type":"string","enum":["auto","photo","document","screenshot","portrait"]},"scale":{"type":"integer","enum":[1,2,4],"description":"Upscale factor (output pixels are capped for safety)."},"level":{"type":"string","enum":["natural","balanced","enhanced","maximum"]},"format":{"type":"string","enum":["auto","jpeg","png","webp","avif"]}}}}}},"responses":{"200":{"description":"Enhanced image (binary)","content":{"image/*":{"schema":{"type":"string","format":"binary"}}}},"400":{"description":"INVALID_REQUEST","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INVALID_REQUEST":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INVALID_REQUEST","message":"The request is invalid."}}}}}}},"401":{"description":"MISSING_API_KEY · INVALID_API_KEY","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"MISSING_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"MISSING_API_KEY","message":"An API key is required. Provide it as 'Authorization: Bearer <key>'."}}},"INVALID_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INVALID_API_KEY","message":"The API key is invalid."}}}}}}},"403":{"description":"INSUFFICIENT_SCOPE · API_ACCESS_NOT_ENABLED","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INSUFFICIENT_SCOPE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INSUFFICIENT_SCOPE","message":"This API key lacks the scope required for this operation."}}},"API_ACCESS_NOT_ENABLED":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"API_ACCESS_NOT_ENABLED","message":"API processing is not enabled for this account."}}}}}}},"413":{"description":"FILE_TOO_LARGE","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"FILE_TOO_LARGE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"FILE_TOO_LARGE","message":"The uploaded file exceeds the maximum allowed size."}}}}}}},"415":{"description":"UNSUPPORTED_FILE_TYPE","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"UNSUPPORTED_FILE_TYPE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"UNSUPPORTED_FILE_TYPE","message":"This file type is not supported."}}}}}}},"422":{"description":"INVALID_DOCUMENT","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INVALID_DOCUMENT":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INVALID_DOCUMENT","message":"The document could not be processed."}}}}}}},"503":{"description":"API_DISABLED","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"API_DISABLED":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"API_DISABLED","message":"The API is temporarily unavailable."}}}}}}}}}},"/documents":{"get":{"tags":["Documents"],"summary":"List stored documents","description":"Requires scope `documents:read`. Lists documents stored by the caller (via OCR with ?store=true). Optional `?filter=all|recent|favorites|trash`.","parameters":[{"name":"filter","in":"query","schema":{"type":"string","enum":["all","recent","favorites","trash"]}}],"responses":{"200":{"description":"Documents","content":{"application/json":{"schema":{"type":"object","required":["success","request_id","api_version","data"],"properties":{"success":{"type":"boolean","enum":[true]},"request_id":{"type":"string","example":"req_9f2c1a7b3d4e5f60"},"api_version":{"type":"string","enum":["v1"]},"data":{"type":"object","properties":{"documents":{"type":"array","items":{"type":"object"}}}}}}}}},"401":{"description":"MISSING_API_KEY","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"MISSING_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"MISSING_API_KEY","message":"An API key is required. Provide it as 'Authorization: Bearer <key>'."}}}}}}},"403":{"description":"INSUFFICIENT_SCOPE","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INSUFFICIENT_SCOPE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INSUFFICIENT_SCOPE","message":"This API key lacks the scope required for this operation."}}}}}}}}}},"/documents/{id}":{"get":{"tags":["Documents"],"summary":"Get a stored document + its OCR result","description":"Requires scope `documents:read`. Ownership-checked.","parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string"}}],"responses":{"200":{"description":"Document + result","content":{"application/json":{"schema":{"type":"object","required":["success","request_id","api_version","data"],"properties":{"success":{"type":"boolean","enum":[true]},"request_id":{"type":"string","example":"req_9f2c1a7b3d4e5f60"},"api_version":{"type":"string","enum":["v1"]},"data":{"type":"object","properties":{"document":{"type":"object"},"result":{"type":"object","nullable":true}}}}}}}},"401":{"description":"MISSING_API_KEY","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"MISSING_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"MISSING_API_KEY","message":"An API key is required. Provide it as 'Authorization: Bearer <key>'."}}}}}}},"403":{"description":"INSUFFICIENT_SCOPE","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INSUFFICIENT_SCOPE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INSUFFICIENT_SCOPE","message":"This API key lacks the scope required for this operation."}}}}}}},"404":{"description":"NOT_FOUND","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"NOT_FOUND":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"NOT_FOUND","message":"The requested resource was not found."}}}}}}}}}},"/documents/{id}/file":{"get":{"tags":["Documents"],"summary":"Download a stored document's original file","description":"Requires scope `documents:read`. Returns the original bytes.","parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string"}}],"responses":{"200":{"description":"Original file (binary)","content":{"application/octet-stream":{"schema":{"type":"string","format":"binary"}}}},"401":{"description":"MISSING_API_KEY","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"MISSING_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"MISSING_API_KEY","message":"An API key is required. Provide it as 'Authorization: Bearer <key>'."}}}}}}},"403":{"description":"INSUFFICIENT_SCOPE","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INSUFFICIENT_SCOPE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INSUFFICIENT_SCOPE","message":"This API key lacks the scope required for this operation."}}}}}}},"404":{"description":"NOT_FOUND","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"NOT_FOUND":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"NOT_FOUND","message":"The requested resource was not found."}}}}}}}}}},"/ocr/export":{"post":{"tags":["Exports"],"summary":"Export OCR text / structured data to a file","description":"Requires scope `exports:read` and API access. JSON body with `format` (txt|json|csv|docx|xlsx|pdf), `text`, optional `structured`/`pages`/`documentType`/`lang`. Returns the exported file as a binary download.","requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["format","text"],"properties":{"format":{"type":"string","enum":["txt","json","csv","docx","xlsx","pdf"]},"text":{"type":"string"},"baseName":{"type":"string"},"documentType":{"type":"string"},"lang":{"type":"string","enum":["en","ar"]}}}}}},"responses":{"200":{"description":"Exported file (binary)","content":{"application/octet-stream":{"schema":{"type":"string","format":"binary"}}}},"400":{"description":"INVALID_REQUEST","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INVALID_REQUEST":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INVALID_REQUEST","message":"The request is invalid."}}}}}}},"401":{"description":"MISSING_API_KEY · INVALID_API_KEY","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"MISSING_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"MISSING_API_KEY","message":"An API key is required. Provide it as 'Authorization: Bearer <key>'."}}},"INVALID_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INVALID_API_KEY","message":"The API key is invalid."}}}}}}},"403":{"description":"INSUFFICIENT_SCOPE · API_ACCESS_NOT_ENABLED","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INSUFFICIENT_SCOPE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INSUFFICIENT_SCOPE","message":"This API key lacks the scope required for this operation."}}},"API_ACCESS_NOT_ENABLED":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"API_ACCESS_NOT_ENABLED","message":"API processing is not enabled for this account."}}}}}}}}}},"/ocr/jobs/{id}":{"get":{"tags":["Jobs"],"summary":"Get async OCR job status and result","description":"Requires scope `ocr:read`.","parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string"}}],"responses":{"200":{"description":"Job status (and result when completed)","content":{"application/json":{"schema":{"type":"object","required":["success","request_id","api_version","data"],"properties":{"success":{"type":"boolean","enum":[true]},"request_id":{"type":"string","example":"req_9f2c1a7b3d4e5f60"},"api_version":{"type":"string","enum":["v1"]},"data":{"$ref":"#/components/schemas/Job"}}}}}},"401":{"description":"MISSING_API_KEY · INVALID_API_KEY","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"MISSING_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"MISSING_API_KEY","message":"An API key is required. Provide it as 'Authorization: Bearer <key>'."}}},"INVALID_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INVALID_API_KEY","message":"The API key is invalid."}}}}}}},"403":{"description":"INSUFFICIENT_SCOPE","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INSUFFICIENT_SCOPE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INSUFFICIENT_SCOPE","message":"This API key lacks the scope required for this operation."}}}}}}},"404":{"description":"JOB_NOT_FOUND","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"JOB_NOT_FOUND":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"JOB_NOT_FOUND","message":"The requested job was not found."}}}}}}}}}},"/webhooks":{"get":{"tags":["Webhooks"],"summary":"List webhook endpoints","description":"Requires scope `webhooks:read`.","responses":{"200":{"description":"Endpoints","content":{"application/json":{"schema":{"type":"object","required":["success","request_id","api_version","data"],"properties":{"success":{"type":"boolean","enum":[true]},"request_id":{"type":"string","example":"req_9f2c1a7b3d4e5f60"},"api_version":{"type":"string","enum":["v1"]},"data":{"type":"object","properties":{"endpoints":{"type":"array","items":{"$ref":"#/components/schemas/WebhookEndpoint"}},"available_events":{"type":"array","items":{"type":"string"}}}}}}}}},"401":{"description":"MISSING_API_KEY","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"MISSING_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"MISSING_API_KEY","message":"An API key is required. Provide it as 'Authorization: Bearer <key>'."}}}}}}},"403":{"description":"INSUFFICIENT_SCOPE","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INSUFFICIENT_SCOPE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INSUFFICIENT_SCOPE","message":"This API key lacks the scope required for this operation."}}}}}}}}},"post":{"tags":["Webhooks"],"summary":"Register a webhook endpoint","description":"Requires scope `webhooks:write`. Returns the signing `secret` ONCE — store it to verify `X-Zegi-Signature` (the legacy `X-AjmanOCR-Signature` header is also sent).","requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["url","events"],"properties":{"url":{"type":"string","format":"uri"},"events":{"type":"array","items":{"type":"string","enum":["ocr.completed","ocr.failed","tool.completed","tool.failed"]}}}}}}},"responses":{"201":{"description":"Created","content":{"application/json":{"schema":{"type":"object","required":["success","request_id","api_version","data"],"properties":{"success":{"type":"boolean","enum":[true]},"request_id":{"type":"string","example":"req_9f2c1a7b3d4e5f60"},"api_version":{"type":"string","enum":["v1"]},"data":{"$ref":"#/components/schemas/WebhookEndpointWithSecret"}}}}}},"400":{"description":"INVALID_REQUEST","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INVALID_REQUEST":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INVALID_REQUEST","message":"The request is invalid."}}}}}}},"401":{"description":"MISSING_API_KEY","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"MISSING_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"MISSING_API_KEY","message":"An API key is required. Provide it as 'Authorization: Bearer <key>'."}}}}}}},"403":{"description":"INSUFFICIENT_SCOPE","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INSUFFICIENT_SCOPE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INSUFFICIENT_SCOPE","message":"This API key lacks the scope required for this operation."}}}}}}}}}},"/webhooks/{id}":{"get":{"tags":["Webhooks"],"summary":"Get a webhook endpoint + recent deliveries","description":"Requires scope `webhooks:read`.","parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string"}}],"responses":{"200":{"description":"Endpoint + deliveries"},"401":{"description":"MISSING_API_KEY","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"MISSING_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"MISSING_API_KEY","message":"An API key is required. Provide it as 'Authorization: Bearer <key>'."}}}}}}},"403":{"description":"INSUFFICIENT_SCOPE","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INSUFFICIENT_SCOPE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INSUFFICIENT_SCOPE","message":"This API key lacks the scope required for this operation."}}}}}}},"404":{"description":"NOT_FOUND","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"NOT_FOUND":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"NOT_FOUND","message":"The requested resource was not found."}}}}}}}}},"delete":{"tags":["Webhooks"],"summary":"Delete a webhook endpoint","description":"Requires scope `webhooks:write`.","parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string"}}],"responses":{"200":{"description":"Deleted"},"401":{"description":"MISSING_API_KEY","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"MISSING_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"MISSING_API_KEY","message":"An API key is required. Provide it as 'Authorization: Bearer <key>'."}}}}}}},"403":{"description":"INSUFFICIENT_SCOPE","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INSUFFICIENT_SCOPE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INSUFFICIENT_SCOPE","message":"This API key lacks the scope required for this operation."}}}}}}},"404":{"description":"NOT_FOUND","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"NOT_FOUND":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"NOT_FOUND","message":"The requested resource was not found."}}}}}}}}}},"/webhooks/{id}/test":{"post":{"tags":["Webhooks"],"summary":"Send a signed test event","description":"Requires scope `webhooks:write`.","parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string"}}],"responses":{"200":{"description":"Test delivery sent"},"401":{"description":"MISSING_API_KEY","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"MISSING_API_KEY":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"MISSING_API_KEY","message":"An API key is required. Provide it as 'Authorization: Bearer <key>'."}}}}}}},"403":{"description":"INSUFFICIENT_SCOPE","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"INSUFFICIENT_SCOPE":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"INSUFFICIENT_SCOPE","message":"This API key lacks the scope required for this operation."}}}}}}},"404":{"description":"NOT_FOUND","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"},"examples":{"NOT_FOUND":{"value":{"success":false,"request_id":"req_9f2c1a7b3d4e5f60","api_version":"v1","error":{"code":"NOT_FOUND","message":"The requested resource was not found."}}}}}}}}}}},"components":{"securitySchemes":{"bearerAuth":{"type":"http","scheme":"bearer","description":"Authorization: Bearer <api_key>"},"apiKeyHeader":{"type":"apiKey","in":"header","name":"X-API-Key","description":"Alternative to the bearer header."}},"schemas":{"ErrorResponse":{"type":"object","required":["success","request_id","api_version","error"],"properties":{"success":{"type":"boolean","enum":[false]},"request_id":{"type":"string"},"api_version":{"type":"string","enum":["v1"]},"error":{"type":"object","required":["code","message"],"properties":{"code":{"type":"string","enum":["MISSING_API_KEY","INVALID_API_KEY","API_KEY_REVOKED","API_KEY_EXPIRED","IP_NOT_ALLOWED","ACCOUNT_INACTIVE","INSUFFICIENT_SCOPE","API_ACCESS_NOT_ENABLED","API_DISABLED","WORKER_UNAVAILABLE","STORAGE_UNAVAILABLE","SERVICE_UNAVAILABLE","RATE_LIMITED","USAGE_LIMIT_EXCEEDED","INVALID_REQUEST","FILE_TOO_LARGE","UNSUPPORTED_FILE_TYPE","INVALID_DOCUMENT","OCR_FAILED","OCR_TIMEOUT","NOT_FOUND","JOB_NOT_FOUND","CONFLICT","SERVER_ERROR"]},"message":{"type":"string"},"details":{"type":"object","additionalProperties":true}}}}},"OcrPage":{"type":"object","properties":{"page":{"type":"integer"},"text":{"type":"string"},"confidence":{"type":"number"},"words":{"type":"array","items":{"$ref":"#/components/schemas/OcrWord"}}}},"OcrWord":{"type":"object","properties":{"text":{"type":"string"},"confidence":{"type":"number"},"bbox":{"type":"array","items":{"type":"integer"},"minItems":4,"maxItems":4}}},"OcrFileResult":{"type":"object","properties":{"name":{"type":"string"},"ok":{"type":"boolean"},"text":{"type":"string"},"confidence":{"type":"number"},"engine":{"type":"string","enum":["paddleocr","tesseract","pdf-text-layer"]},"language":{"type":"string"},"document_type":{"type":"string"},"structured":{"type":"object","additionalProperties":true,"nullable":true},"pages":{"type":"array","items":{"$ref":"#/components/schemas/OcrPage"}}}},"JobAccepted":{"type":"object","properties":{"job_id":{"type":"string"},"status":{"type":"string","example":"queued"},"status_url":{"type":"string","format":"uri"},"created_at":{"type":"string","format":"date-time"}}},"Job":{"type":"object","properties":{"job_id":{"type":"string"},"status":{"type":"string","enum":["queued","processing","completed","failed","expired","cancelled"]},"filename":{"type":"string"},"pages":{"type":"integer"},"engine":{"type":"string"},"created_at":{"type":"string","format":"date-time"},"completed_at":{"type":"string","format":"date-time","nullable":true},"result":{"type":"object","additionalProperties":true}}},"Account":{"type":"object","properties":{"account":{"type":"object","properties":{"id":{"type":"string"},"type":{"type":"string","enum":["personal","organization"]},"status":{"type":"string"}}},"api_key":{"type":"object","properties":{"key_prefix":{"type":"string"},"scopes":{"type":"array","items":{"type":"string","enum":["ocr:read","ocr:process","documents:read","documents:write","compression:read","compression:process","exports:read","usage:read","webhooks:read","webhooks:write","pdf:merge","pdf:split","pdf:convert","pdf:searchable","image:enhance"]}}}},"plan":{"type":"object","properties":{"key":{"type":"string"},"name":{"type":"string"}}},"api_access_enabled":{"type":"boolean"},"usage":{"type":"object","properties":{"pages_used":{"type":"integer"},"pages_allowed":{"type":"integer","nullable":true},"pages_remaining":{"type":"integer","nullable":true},"unlimited":{"type":"boolean"}}},"limits":{"type":"object","properties":{"max_file_bytes":{"type":"integer"},"max_pages_per_request":{"type":"integer"},"max_batch_files":{"type":"integer"}}}}},"WebhookEndpoint":{"type":"object","properties":{"id":{"type":"string"},"url":{"type":"string","format":"uri"},"events":{"type":"array","items":{"type":"string"}},"active":{"type":"boolean"},"createdAt":{"type":"string","format":"date-time"}}},"WebhookEndpointWithSecret":{"allOf":[{"$ref":"#/components/schemas/WebhookEndpoint"},{"type":"object","properties":{"secret":{"type":"string","description":"Signing secret — shown once."}}}]}}}}