{"openapi":"3.0.3","info":{"title":"Kadoa API","version":"3.0.0","contact":{"name":"Support","email":"support@kadoa.com"}},"servers":[{"url":"https://api.kadoa.com"}],"paths":{"/v4/changes":{"get":{"summary":"Get all data changes","tags":["Workflows"],"parameters":[{"name":"x-api-key","in":"header","required":false,"description":"API key for authorization","schema":{"type":"string"}},{"name":"Authorization","in":"header","required":false,"description":"Bearer token for authorization","schema":{"type":"string"}},{"name":"workflowIds","in":"query","required":false,"description":"Comma-separated list of workflow IDs. If not provided, returns changes for all ACTIVE workflows","schema":{"type":"string"}},{"name":"startDate","in":"query","required":false,"description":"Start date to filter changes (ISO format)","schema":{"type":"string","format":"date-time"}},{"name":"endDate","in":"query","required":false,"description":"End date to filter changes (ISO format, inclusive). A date-only value such as `2024-03-01` covers that whole day.","schema":{"type":"string","format":"date-time"}},{"name":"skip","in":"query","required":false,"description":"Number of records to skip for pagination","schema":{"type":"integer"}},{"name":"limit","in":"query","required":false,"description":"Number of records to return for pagination","schema":{"type":"integer"}},{"name":"exclude","in":"query","required":false,"description":"Comma-separated list of fields to exclude from each change object (e.g., \"data,differences\")","schema":{"type":"string","example":"data,differences"}}],"security":[{"ApiKeyAuth":[]},{"BearerAuth":[]}],"responses":{"200":{"description":"Workflow changes returned successfully","content":{"application/json":{"schema":{"type":"object","properties":{"timestamp":{"type":"string","format":"date-time","description":"Timestamp of the response"},"changesCount":{"type":"integer","description":"Total number of changes found"},"changes":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string","description":"Unique identifier of the change"},"workflowId":{"type":"string","description":"ID of the workflow this change belongs to"},"data":{"type":"array","nullable":true,"description":"Current state of the data after the change","items":{"type":"object"}},"dataPending":{"type":"boolean","description":"True when durable change data is still being stored; change events are emitted first so users see changes as fast as possible."},"differences":{"type":"array","description":"Structured representation of changes with object-based diffing. List responses omit visualDiff metadata. Pass `exclude=differences` to omit this large field; counts are still returned via `differencesCounts`.","items":{"type":"object","properties":{"type":{"type":"string","description":"Type of change (added, removed, or changed)","enum":["added","removed","changed"]},"fields":{"type":"array","description":"List of field changes","items":{"type":"object","properties":{"key":{"type":"string","description":"Field name"},"value":{"type":"string","description":"Current field value"},"previousValue":{"type":"string","description":"Previous field value (only present for changed type)"}}}}}}},"differencesCounts":{"type":"object","nullable":true,"description":"Pre-computed counts of differences by type. Always returned (even when `exclude=differences`) so list views can render summary badges without downloading the full diff.","properties":{"added":{"type":"integer"},"removed":{"type":"integer"},"changed":{"type":"integer"}}},"url":{"type":"string","description":"URL where the change was detected"},"summary":{"type":"string","nullable":true,"description":"AI-generated one-sentence summary of the data change. Null if generation failed, feature is disabled, or change predates the feature."},"screenshotUrl":{"type":"string","description":"URL of the screenshot taken when the change was detected"},"createdAt":{"type":"string","format":"date-time","description":"Timestamp when the change was created"}}}},"pagination":{"type":"object","properties":{"totalCount":{"type":"integer","description":"Total number of changes found"},"page":{"type":"integer","description":"Current page number"},"totalPages":{"type":"integer","description":"Total number of pages"},"limit":{"type":"integer","description":"Number of records per page"}}}}}}}},"400":{"description":"Bad request (invalid date range or workflow IDs)"},"401":{"description":"Unauthorized (invalid or missing API key or Bearer token)"},"500":{"description":"Internal server error"}},"x-code-samples":[{"lang":"curl","source":"curl -X GET \"https://api.kadoa.com/v4/changes?workflowIds=123,456&startDate=2024-01-01T00:00:00Z&endDate=2024-03-01T00:00:00Z\" \\\n-H \"x-api-key: YOUR_API_KEY\"\n\n# Exclude data and differences fields for smaller response\ncurl -X GET \"https://api.kadoa.com/v4/changes?workflowIds=123,456&exclude=data,differences\" \\\n-H \"x-api-key: YOUR_API_KEY\"\n"},{"lang":"python","source":"import requests\n\nurl = \"https://api.kadoa.com/v4/changes\"\nheaders = {\n    \"x-api-key\": \"YOUR_API_KEY\"\n}\nparams = {\n    \"workflowIds\": \"123,456\",\n    \"startDate\": \"2024-01-01T00:00:00Z\",\n    \"endDate\": \"2024-03-01T00:00:00Z\"\n}\n\nresponse = requests.get(url, headers=headers, params=params)\ndata = response.json()\nprint(data)\n\n# Exclude data and differences fields for smaller response\nparams[\"exclude\"] = \"data,differences\"\nresponse = requests.get(url, headers=headers, params=params)\ndata = response.json()\nprint(data)\n"}]}},"/v4/changes/{changeId}":{"get":{"summary":"Get data change by ID","tags":["Workflows"],"parameters":[{"name":"x-api-key","in":"header","required":false,"description":"API key for authorization","schema":{"type":"string"}},{"name":"Authorization","in":"header","required":false,"description":"Bearer token for authorization","schema":{"type":"string"}},{"name":"changeId","in":"path","required":true,"description":"ID of the workflow change to retrieve","schema":{"type":"string"}}],"security":[{"ApiKeyAuth":[]},{"BearerAuth":[]}],"responses":{"200":{"description":"Workflow change returned successfully","content":{"application/json":{"schema":{"type":"object","properties":{"id":{"type":"string","description":"Unique identifier of the change"},"workflowId":{"type":"string","description":"ID of the workflow this change belongs to"},"data":{"type":"array","nullable":true,"description":"Current state of the data after the change","items":{"type":"object"}},"dataPending":{"type":"boolean","description":"True when durable change data is still being stored; change events are emitted first so users see changes as fast as possible."},"differences":{"type":"array","description":"Structured representation of changes with object-based diffing","items":{"type":"object","properties":{"type":{"type":"string","description":"Type of change (added, removed, or changed)","enum":["added","removed","changed"]},"fields":{"type":"array","description":"List of field changes","items":{"type":"object","properties":{"key":{"type":"string","description":"Field name"},"value":{"type":"string","description":"Current field value"},"previousValue":{"type":"string","description":"Previous field value (only present for changed type)"}}}},"visualDiff":{"type":"object","nullable":true,"description":"Screenshot-space boxes for this diff item. Present only when row grounding is available.","properties":{"current":{"type":"object","description":"Boxes on the current change screenshot for added or changed rows.","properties":{"url":{"type":"string"},"width":{"type":"number"},"height":{"type":"number"},"rowBox":{"type":"object","properties":{"x":{"type":"number"},"y":{"type":"number"},"width":{"type":"number"},"height":{"type":"number"}}},"fieldBoxes":{"type":"object","additionalProperties":{"type":"object","properties":{"x":{"type":"number"},"y":{"type":"number"},"width":{"type":"number"},"height":{"type":"number"}}}}}},"previous":{"type":"object","description":"Boxes on the previous workflow job screenshot for removed or changed rows.","properties":{"url":{"type":"string"},"width":{"type":"number"},"height":{"type":"number"},"rowBox":{"type":"object","properties":{"x":{"type":"number"},"y":{"type":"number"},"width":{"type":"number"},"height":{"type":"number"}}},"fieldBoxes":{"type":"object","additionalProperties":{"type":"object","properties":{"x":{"type":"number"},"y":{"type":"number"},"width":{"type":"number"},"height":{"type":"number"}}}}}}}}}}},"url":{"type":"string","description":"URL where the change was detected"},"summary":{"type":"string","nullable":true,"description":"AI-generated one-sentence summary of the data change. Null if generation failed, feature is disabled, or change predates the feature."},"screenshotUrl":{"type":"string","description":"URL of the screenshot taken when the change was detected"},"previousJobScreenshotUrl":{"type":"string","nullable":true,"description":"Screenshot URL from the previous workflow job used by visualDiff.previous boxes."},"createdAt":{"type":"string","format":"date-time","description":"Timestamp when the change was created"}}}}}},"400":{"description":"Bad request (invalid change ID format)"},"401":{"description":"Unauthorized (invalid or missing API key or Bearer token)"},"403":{"description":"Forbidden (no access to the workflow or workflow not real-time enabled)"},"404":{"description":"Change not found"},"500":{"description":"Internal server error"}},"x-code-samples":[{"lang":"curl","source":"curl -X GET \"https://api.kadoa.com/v4/changes/123456789\" \\\n-H \"x-api-key: YOUR_API_KEY\"\n"},{"lang":"python","source":"import requests\n\nurl = \"https://api.kadoa.com/v4/changes/123456789\"\nheaders = {\n    \"x-api-key\": \"YOUR_API_KEY\"\n}\n\nresponse = requests.get(url, headers=headers)\ndata = response.json()\nprint(data)\n"}]}},"/v4/changes/files/{encodedPath}":{"get":{"summary":"Download a change PDF file","tags":["Workflows"],"parameters":[{"name":"x-api-key","in":"header","required":false,"description":"API key for authorization","schema":{"type":"string"}},{"name":"Authorization","in":"header","required":false,"description":"Bearer token for authorization","schema":{"type":"string"}},{"name":"encodedPath","in":"path","required":true,"description":"Base64-encoded file path","schema":{"type":"string"}}],"security":[{"ApiKeyAuth":[]},{"BearerAuth":[]}],"responses":{"200":{"description":"PDF file stream","content":{"application/pdf":{"schema":{"type":"string","format":"binary"}}}},"400":{"description":"Bad request (invalid file path)"},"401":{"description":"Unauthorized (invalid or missing API key or Bearer token)"},"404":{"description":"File not found"},"500":{"description":"Internal server error"}}}},"/v4/files/{fileName}":{"get":{"summary":"Download a file","description":"Downloads a specific file from the storage","tags":["Files"],"security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"fileName","in":"path","required":true,"description":"Name of the file to download","schema":{"type":"string"}}],"responses":{"200":{"description":"File content","content":{"application/octet-stream":{"schema":{"type":"string","format":"binary","description":"File content in its original format"}}}},"400":{"description":"Bad request - File name is required or invalid"},"401":{"description":"Unauthorized - Authentication required"},"403":{"description":"Forbidden - Insufficient permissions"},"404":{"description":"File not found"},"500":{"description":"Internal server error"}}}},"/v4/files/bulk-download":{"post":{"summary":"Download multiple files as a ZIP archive","description":"Downloads multiple files from the storage and returns them as a ZIP archive","tags":["Files"],"security":[{"ApiKeyAuth":[]}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["files"],"properties":{"files":{"type":"array","items":{"type":"string"},"description":"List of file names to download"}}}}}},"responses":{"200":{"description":"ZIP archive containing the requested files","content":{"application/zip":{"schema":{"type":"string","format":"binary","description":"ZIP archive containing the requested files"}}}},"400":{"description":"Bad request - Files list is required or invalid"},"401":{"description":"Unauthorized - Authentication required"},"403":{"description":"Forbidden - Insufficient permissions"},"500":{"description":"Internal server error"}}}},"/v4/locations":{"get":{"summary":"Get all available locations","tags":["Locations"],"security":[{"ApiKeyAuth":[]}],"responses":{"200":{"description":"List of available locations","content":{"application/json":{"schema":{"type":"object","properties":{"locations":{"type":"array","items":{"type":"object","properties":{"countryName":{"type":"string","description":"Full name of the country"},"isoCode":{"type":"string","description":"Two-letter ISO country code in uppercase"}}}}}}}}},"401":{"description":"Unauthorized access, either due to missing or invalid x-api-key"}}}},"/v4/support/issues":{"get":{"summary":"Get support issues for the current customer","tags":["Support"],"security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"includeResolved","in":"query","required":false,"schema":{"type":"string","enum":["true","false"],"default":"false"},"description":"When true, includes resolved issues in the response. Defaults to false."},{"name":"workflowId","in":"query","required":false,"schema":{"type":"string"},"description":"When set, only returns issues attached to this workflow."}],"responses":{"200":{"description":"List of support issues","content":{"application/json":{"schema":{"type":"object","properties":{"issues":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string","format":"uuid","description":"Support request ID"},"teamId":{"type":"string","format":"uuid","description":"Team that owns the issue"},"workflowId":{"type":"string","format":"uuid","description":"Linked workflow ID (if any)"},"workflowName":{"type":"string","description":"Name of the linked workflow"},"issueId":{"type":"string","description":"Kadoa issue identifier (e.g. KAD-1234)"},"requestedAt":{"type":"string","format":"date-time","description":"When the issue was created"},"resolvedAt":{"type":"string","format":"date-time","nullable":true,"description":"When the issue was resolved (null if open)"},"resolvedBy":{"type":"string","nullable":true,"description":"Who resolved the issue"},"issueTitle":{"type":"string","description":"Issue title"},"issueDescription":{"type":"string","description":"Issue description"},"status":{"type":"string","description":"Current status (e.g. Triage, Todo, In Progress, Done)"},"priority":{"type":"number","description":"Priority level (0=No priority, 1=Urgent, 2=High, 3=Medium, 4=Low)"},"labels":{"type":"array","items":{"type":"string"},"description":"Labels attached to the issue"},"updatedAt":{"type":"string","format":"date-time","description":"Last update timestamp"},"resolutionMessage":{"type":"string","nullable":true,"description":"Message explaining how the issue was resolved (null if not provided or issue is open)"}}}}}},"example":{"issues":[{"id":"a1b2c3d4-e5f6-7890-abcd-ef1234567890","teamId":"f0e1d2c3-b4a5-6789-0abc-def123456789","workflowId":"12345678-abcd-ef01-2345-6789abcdef01","workflowName":"Product catalog scraper","issueId":"KAD-1234","requestedAt":"2026-03-18T09:15:00.000Z","resolvedAt":"2026-03-18T10:32:12.000Z","resolvedBy":"support-agent","issueTitle":"Missing price fields on product pages","issueDescription":"Several product pages are returning null for the price field. Affected URLs include the seasonal sale section.","status":"Done","priority":2,"labels":[],"updatedAt":"2026-03-18T10:32:00.000Z","resolutionMessage":"Updated the CSS selectors to handle the new page layout."}]}}}}}},"post":{"summary":"Create a new support issue","description":"Creates a support ticket. User info is inferred from auth context.","tags":["Support"],"security":[{"ApiKeyAuth":[]}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["title","category","description"],"properties":{"title":{"type":"string","description":"Issue title"},"category":{"type":"string","enum":["bug","feature","workflow_issue","template_issue","integration","billing","data_diff"]},"priority":{"type":"number","enum":[0,1,2,3,4]},"description":{"type":"string"},"files":{"type":"array","description":"File attachments to include with the issue. Each file must already be hosted at a publicly accessible URL.","items":{"type":"object","required":["name","url","type","size"],"properties":{"name":{"type":"string","description":"File name (e.g. screenshot.png)"},"url":{"type":"string","description":"Publicly accessible URL of the file"},"type":{"type":"string","description":"MIME type (e.g. image/png, application/pdf)"},"size":{"type":"number","description":"File size in bytes"}}}},"workflowId":{"type":"string","description":"Optional workflow ID to link the issue"},"templateId":{"type":"string","format":"uuid","description":"Optional template ID to link the issue. Only relevant when category is template_issue."},"dataChangeId":{"type":"string","description":"ID of a data change from the Data Changes API (GET /v4/changes). Links the support issue to a specific data diff so the team can review the exact change being reported. Only relevant when category is data_diff."},"subcategory":{"type":"string","enum":["wrong_data","missing_fields","wrong_website","scraper_broken","other","integration_slack","integration_snowflake","integration_cloud_storage","integration_databricks","integration_sftp","integration_sdk","integration_other"],"description":"Optional subcategory for workflow or integration issues"},"jobId":{"type":"string","format":"uuid","description":"Optional ID of the workflow run the issue is about."},"copilotSessionId":{"type":"string","format":"uuid","description":"Kadoa Assistant session the issue was raised from. Must be a session of the caller's team. Marks the ticket as assistant-created and links the session for support."}}}}}},"responses":{"202":{"description":"Issue creation accepted, or skipped when the ticket is not eligible (skipped is true and reason explains why)","content":{"application/json":{"schema":{"type":"object","properties":{"success":{"type":"boolean"},"issueId":{"type":"string","description":"Local support request ID"},"supportRequestId":{"type":"string","description":"Local support request ID"},"jobId":{"type":"string","description":"Engine event job ID"},"status":{"type":"string","enum":["accepted"]},"skipped":{"type":"boolean","description":"True when no ticket was filed"},"reason":{"type":"string","description":"Why the ticket was skipped"},"code":{"type":"string","description":"Machine-readable skip code"}}}}}},"409":{"description":"The linked workflow already has an open support issue","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"string"},"supportRequestId":{"type":"string"},"issueId":{"type":"string"}}}}}}}}},"/v4/support/states":{"get":{"summary":"Get available issue states","tags":["Support"],"security":[{"ApiKeyAuth":[]}],"responses":{"200":{"description":"List of available states","content":{"application/json":{"schema":{"type":"object","properties":{"states":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string","description":"State ID (use this when updating an issue)"},"name":{"type":"string","description":"Human-readable state name"},"position":{"type":"number","description":"Display order position"},"type":{"type":"string","description":"State type (e.g. triage, unstarted, started, completed, canceled)"}}}}}},"example":{"states":[{"id":"2d70fae6-0805-47f5-9f6f-49f2edb9c1be","name":"Triage","position":0,"type":"triage"},{"id":"2b23aac3-4b57-46de-a551-cf823758a6de","name":"In Review","position":1002,"type":"started"},{"id":"dec8f12f-33d6-4e4b-bd9e-431caba0d0b5","name":"Todo","position":1,"type":"unstarted"},{"id":"d5171eb1-0479-45fd-acf4-502a6874eb89","name":"In Progress","position":2,"type":"started"},{"id":"ba3f8aed-c34e-44fb-83f8-86142df48a12","name":"Duplicate","position":5,"type":"canceled"},{"id":"a0a782d4-1295-4c11-9ac4-e1462d8c6c58","name":"Done","position":3,"type":"completed"},{"id":"5eee6b17-12a5-44ed-b17e-daf16686a5ee","name":"Backlog","position":0,"type":"backlog"},{"id":"0fd73e82-b7c0-4f21-b65f-3dd0871f7a11","name":"Canceled","position":4,"type":"canceled"}]}}}}}}},"/v4/support/attachments":{"post":{"summary":"Upload support ticket attachments","description":"Uploads files to Linear's asset storage and returns their asset URLs for use in a subsequent issue creation. Multipart form data with a \"files\" field (max 10 files, 25MB each).\n","tags":["Support"],"security":[{"ApiKeyAuth":[]}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"type":"object","properties":{"files":{"type":"array","items":{"type":"string","format":"binary"}}}}}}},"responses":{"200":{"description":"Uploaded files with Linear asset URLs"}}}},"/v4/support/issues/{issueId}":{"patch":{"summary":"Update issue priority and/or status","tags":["Support"],"security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"issueId","in":"path","required":true,"schema":{"type":"string"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"priority":{"type":"number","enum":[0,1,2,3,4],"description":"Issue priority (0=No priority, 1=Urgent, 2=High, 3=Medium, 4=Low)"},"stateId":{"type":"string","description":"Target state ID. Use GET /v4/support/states to retrieve available states. Setting a non-final state on a resolved issue will reopen it."},"reopenComment":{"type":"string","description":"Optional comment explaining why the issue is being reopened. Max 2000 characters. Only used when reopening a resolved issue."},"resolutionMessage":{"type":"string","description":"Optional message explaining how the issue was resolved. Max 2000 characters. When provided, a resolved email including this message is sent to the user."}}}}}},"responses":{"200":{"description":"Issue updated successfully"}}}},"/v4/workflows/{workflowId}/auditlog":{"get":{"summary":"Get workflow audit log entries","tags":["Workflows"],"parameters":[{"name":"x-api-key","in":"header","required":false,"description":"API key for authorization","schema":{"type":"string"}},{"name":"Authorization","in":"header","required":false,"description":"Bearer token for authorization","schema":{"type":"string"}},{"name":"workflowId","in":"path","required":true,"description":"ID of the workflow to retrieve audit logs from","schema":{"type":"string"}},{"name":"page","in":"query","required":false,"description":"Page number for pagination","schema":{"type":"integer","minimum":1,"default":1}},{"name":"limit","in":"query","required":false,"description":"Number of items per page","schema":{"type":"integer","minimum":1,"default":25}}],"security":[{"ApiKeyAuth":[]},{"BearerAuth":[]}],"responses":{"200":{"description":"Workflow audit log entries returned successfully","content":{"application/json":{"schema":{"type":"object","required":["id","timestamp","logEntriesCount","logEntries","pagination"],"properties":{"id":{"type":"string","description":"Workflow ID"},"timestamp":{"type":"string","format":"date-time","description":"Timestamp of the response"},"logEntriesCount":{"type":"integer","description":"Total number of log entries"},"logEntries":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string","description":"Audit log entry ID"},"operationType":{"type":"string","enum":["CREATE","UPDATE","DELETE"],"description":"Type of operation performed"},"userId":{"type":"string","description":"ID of the user who performed the operation"},"userEmail":{"type":"string","description":"Email of the user who performed the operation"},"previousValue":{"type":"object","description":"Previous state of the workflow"},"newValue":{"type":"object","description":"New state of the workflow"},"createdAt":{"type":"string","format":"date-time","description":"Timestamp when the operation was performed"},"requestSource":{"type":"string","nullable":true,"enum":["UI","API","SDK","MCP","CLI","ASSISTANT","SYSTEM"],"description":"Channel that originated the change"},"authMethod":{"type":"string","nullable":true,"description":"Authentication method used (e.g. JWT_TOKEN, PERSONAL_API_KEY, TEAM_API_KEY, SYSTEM)"}}}},"pagination":{"type":"object","properties":{"page":{"type":"integer","description":"Current page number"},"limit":{"type":"integer","description":"Number of items per page"},"totalPages":{"type":"integer","description":"Total number of pages"},"totalCount":{"type":"integer","description":"Total number of log entries"}}}}}}}},"400":{"description":"Bad request (invalid parameters)"},"401":{"description":"Unauthorized (invalid or missing API key or Bearer token)"},"404":{"description":"Workflow not found"},"500":{"description":"Internal server error"}}}},"/v4/workflows/bulk":{"post":{"summary":"Perform bulk operations on multiple workflows","description":"Execute actions on multiple workflows at once. Best-effort processing - each workflow is processed independently. The 'approve' action approves preview data for workflows in PREVIEW state. The 'stop' action cancels each workflow's running job without changing its schedule.","tags":["Workflows"],"security":[{"ApiKeyAuth":[]}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["workflowIds","action"],"properties":{"workflowIds":{"type":"array","items":{"type":"string"},"maxItems":50,"description":"Array of workflow IDs to operate on (max 50)","example":["507f1f77bcf86cd799439011","507f1f77bcf86cd799439012"]},"action":{"type":"string","enum":["run","pause","resume","stop","delete","approve","assignTags"],"description":"The action to perform on all workflows"},"params":{"type":"object","description":"Action-specific parameters","properties":{"tags":{"type":"array","items":{"type":"string"},"description":"Tags to assign (required for assignTags action)"}}}}}}}},"responses":{"200":{"description":"Bulk operation processed (check results for individual outcomes)","content":{"application/json":{"schema":{"type":"object","properties":{"results":{"type":"array","items":{"type":"object","properties":{"workflowId":{"type":"string"},"success":{"type":"boolean"},"error":{"type":"string","description":"Error message if success is false"},"jobId":{"type":"string","description":"Job ID of the started run (run action, or approve when previewRestarted)"},"previewRestarted":{"type":"boolean","description":"Approve found the preview out of date and started a new preview run (jobId) instead; the workflow stays in PREVIEW."}}}},"summary":{"type":"object","properties":{"total":{"type":"integer"},"succeeded":{"type":"integer","description":"Workflows the action was applied to; excludes restarted previews"},"failed":{"type":"integer"},"previewRestarted":{"type":"integer","description":"Approvals that started a new preview run instead of approving"}}}}}}}},"400":{"description":"Invalid request","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"string"}}}}}},"401":{"description":"Unauthorized"},"403":{"description":"Forbidden"}}}},"/v4/workflows/{workflowId}":{"get":{"summary":"Get workflow by ID","tags":["Workflows"],"parameters":[{"name":"workflowId","in":"path","required":true,"description":"ID of the workflow to retrieve","schema":{"type":"string"}}],"security":[{"ApiKeyAuth":[]}],"responses":{"200":{"description":"Workflow details retrieved successfully","content":{"application/json":{"schema":{"type":"object","properties":{"id":{"type":"string","description":"Unique identifier for the workflow"},"name":{"type":"string","description":"Name of the workflow"},"description":{"type":"string","description":"Description of the workflow"},"state":{"type":"string","enum":["ACTIVE","DRAFT","ERROR","PAUSED","NOT_SUPPORTED","PREVIEW","COMPLIANCE_REVIEW","COMPLIANCE_REJECTED","QUEUED","SETUP","DELETED"],"description":"Persisted state of the long-lived workflow. It may describe setup or a control state such as ACTIVE or PAUSED. Use displayState for operational status UI."},"displayState":{"type":"string","enum":["ACTIVE","DRAFT","ERROR","PAUSED","NOT_SUPPORTED","PREVIEW","QUEUED","SETUP","PENDING_START","RUNNING","VALIDATING","FAILED","DEGRADED","COMPLIANCE_REVIEW","COMPLIANCE_REJECTED","DELETED","STOPPED"],"description":"Computed operational summary based on workflow state, the latest run, and monitor health. It does not indicate pending user input or support ownership; use awaitingUserInput and inSupport for those. ACTIVE may be presented as Complete, Scheduled, or Running depending on workflow type and schedule."},"reviewReason":{"type":"string","enum":["COMPLIANCE_REVIEW","HARD_FAIL","TRANSFORMATION_REPAIR_REQUIRED","MINIMUM_HUMAN_APPROVALS","DATA_QUALITY_SCHEMA_ADHERENCE","DATA_QUALITY_SCHEMA_VALIDATION","DATA_QUALITY_COMPLETENESS","DATA_QUALITY_SEMANTIC_PLAUSIBILITY","ROW_COUNT_CHANGED","WORKFLOW_REVISION_DRIFT","ZERO_RESULTS"],"description":"Why the latest run is being verified. Only present while displayState is VALIDATING."},"userId":{"type":"string","description":"ID of the user who owns the workflow"},"userName":{"type":"string","description":"Display name of the workflow owner"},"userEmail":{"type":"string","format":"email","description":"Email of the workflow owner"},"createdAt":{"type":"string","format":"date-time","description":"Timestamp when the workflow was created"},"updateInterval":{"type":"string","description":"Update frequency"},"isRealTime":{"type":"boolean","description":"Whether this workflow should be displayed as realtime"},"lastDataChangedAt":{"type":"string","format":"date-time","nullable":true,"description":"Most recent persisted customer-visible data change for a real-time workflow"},"schedules":{"type":"array","items":{"type":"string"},"description":"Cron schedules for updates"},"scheduleTimezone":{"type":"string","example":"America/New_York","description":"IANA timezone used to evaluate cron schedules"},"nextInvocation":{"type":"string","format":"date-time","description":"Next scheduled execution time"},"monitoring":{"type":"boolean","description":"Whether monitoring is enabled"},"location":{"type":"object","properties":{"type":{"type":"string","enum":["auto","manual"]},"isoCode":{"type":"string","description":"Supported country ISO code when type is manual"}},"description":"Scraping location configuration"},"tags":{"type":"array","items":{"type":"string"},"description":"Tags associated with the workflow"},"schemaName":{"type":"string","description":"Name of the schema used"},"schemaId":{"type":"string","description":"ID of the schema used"},"templateName":{"type":"string","nullable":true,"description":"Name of the linked workflow template"},"templateId":{"type":"string","nullable":true,"description":"ID of the linked workflow template"},"templateVersion":{"type":"integer","nullable":true,"description":"Applied template version"},"templateHasPrompt":{"type":"boolean","description":"Whether the template controls the workflow prompt"},"templateHasSchema":{"type":"boolean","description":"Whether the template controls the extraction schema"},"templateHasSchemaValidationRules":{"type":"boolean","description":"Whether the template controls schema validation rules"},"templateHasNotifications":{"type":"boolean","description":"Whether the template controls notification settings"},"templateHasFrequency":{"type":"boolean","description":"Whether the template controls schedule/frequency"},"templateHasRecordLimit":{"type":"boolean","description":"Whether the template controls the output record limit"},"hasSchemaValidationRules":{"type":"boolean","description":"Whether this workflow has schema validation rules"},"channelCounts":{"type":"object","additionalProperties":{"type":"integer"},"description":"Notification channel counts grouped by channel type"},"jobId":{"type":"string","description":"ID of the latest operational run attempt"},"publishedJobId":{"type":"string","description":"ID of the latest finished run that supplies customer-visible data"},"isFirstRun":{"type":"boolean","description":"Whether the workflow has not completed a regular run yet"},"dataQualityIssues":{"type":"integer","description":"Number of data-quality issues in the latest finished run"},"finishedAt":{"type":"string","format":"date-time","description":"When the last job finished"},"startedAt":{"type":"string","format":"date-time","description":"When the last job started"},"estimatedFinishedAtUtc":{"type":"string","format":"date-time","nullable":true,"description":"Estimated UTC finish time for the active job, when available."},"dataKey":{"type":"string","description":"Database key for the workflow data"},"errors":{"type":"array","description":"Errors from the last job run","items":{"type":"object","properties":{"errorCode":{"type":"string","description":"Error code identifying the type of error"},"message":{"type":"string","description":"Human-readable error message"},"timestamp":{"type":"string","format":"date-time","description":"When the error occurred"},"screenshot":{"type":"string","description":"Optional screenshot URL"},"context":{"type":"object","description":"Additional context about the error"}}}},"runState":{"type":"string","enum":["RUNNING","FINISHED","FAILED","STOPPED"],"description":"State of the latest execution attempt. Use this for run diagnostics or workflow history, not as the workflow lifecycle or status label."},"totalRecords":{"type":"integer","description":"Total number of records extracted"},"url":{"type":"string","description":"Primary URL being scraped"},"urls":{"type":"array","items":{"type":"string"},"description":"List of URLs being scraped"},"browserActions":{"type":"array","description":"Optional browser actions to perform before extraction","items":{"type":"object","properties":{"type":{"type":"string","description":"Action type (e.g., CLICK, TYPE, WAIT, GOTO)"},"selector":{"type":"string","description":"CSS selector for element-based actions"},"text":{"type":"string","description":"Text to type for TYPE actions"},"timeMs":{"type":"integer","description":"Milliseconds to wait for WAIT actions"},"url":{"type":"string","description":"URL to navigate to for GOTO actions"}}}},"schema":{"type":"array","items":{"type":"object","properties":{"name":{"type":"string"},"description":{"type":"string"},"example":{"type":"string"},"dataType":{"type":"string","enum":["STRING","NUMBER","BOOLEAN","DATE","DATETIME","CURRENCY","MONEY","IMAGE","LINK","OBJECT","ARRAY"]},"isKey":{"type":"boolean"},"isRequired":{"type":"boolean"},"isUnique":{"type":"boolean"}}},"description":"Extraction schema fields"},"transformation":{"type":"object","nullable":true,"description":"The workflow's transformation: the input fields it reads as context and the output fields it adds or modifies, each with a one-sentence customer summary. Null when the workflow has no transformation.","properties":{"contextFields":{"type":"array","items":{"type":"string"},"description":"Input fields the transformation reads as mapping context. Absent when the step reads the full row."},"fields":{"type":"array","items":{"type":"object","properties":{"name":{"type":"string"},"summary":{"type":"string","nullable":true},"type":{"type":"string","enum":["STRING","NUMBER","BOOLEAN","DATE","DATETIME","CURRENCY","MONEY","IMAGE","LINK","OBJECT","ARRAY"],"description":"Field data type"}}}}}},"entity":{"type":"string","description":"Canonical extracted entity name"},"extractionSpec":{"type":"object","additionalProperties":true,"description":"Canonical extraction intent for Assistant-built workflows"},"isSchemaEditable":{"type":"boolean","description":"Whether the schema can be edited"},"limit":{"type":"integer","description":"Maximum number of items to scrape"},"additionalData":{"type":"object","description":"Additional static data for the workflow"},"notificationConfig":{"type":"object","nullable":true,"properties":{"monitoredFields":{"type":"array","items":{"type":"object","required":["fieldName","operator"],"properties":{"fieldName":{"type":"string"},"operator":{"type":"string","enum":["changed","added","removed"]},"isKeyField":{"type":"boolean"}}}},"conditions":{"type":"object","additionalProperties":true,"description":"Persisted AND/OR monitoring condition group"}},"description":"Current monitoring configuration. Use these values as the basis for replacement updates."},"openSupportRequests":{"type":"array","description":"List of open support requests for this workflow. Only present when there are open requests.","items":{"type":"object","properties":{"issueId":{"type":"string","nullable":true,"description":"Linear issue identifier (e.g., KAD-123)"},"requestedAt":{"type":"string","format":"date-time","description":"When the support request was created"},"status":{"type":"string","description":"Customer-visible ticket status synced from Linear (e.g., In Progress). Absent until the first sync."},"statusType":{"type":"string","description":"Status category backing `status` (e.g., unstarted, started, completed)"}}}},"inSupport":{"type":"boolean","description":"True when Kadoa support has an open ticket on this workflow. Same predicate as the inSupport query filter. Independent of state/displayState: this answers who is handling the workflow, while displayState answers whether it is delivering data. Prefer this over recomputing from openSupportRequests."},"observerHealth":{"type":"object","nullable":true,"description":"Health status for monitored workflows. Only present when health monitoring is active and detects issues.","properties":{"healthTier":{"type":"string","enum":["HEALTHY","WARNING","DEGRADED","UNHEALTHY","FAILED"],"description":"Current health tier"},"reason":{"type":"string","description":"Human-readable explanation of the health status"},"issueStartedAt":{"type":"string","format":"date-time","description":"When the current degradation episode started"},"lastCheckedAt":{"type":"string","format":"date-time","description":"When health was last evaluated"}}},"extractionStrategySummary":{"allOf":[{"$ref":"#/components/schemas/ExtractionStrategySummary"}],"nullable":true,"description":"Customer-safe extraction strategy: from workflow metadata for custom SCRIPT workflows, else from the latest completed build. Suppressed while an Assistant setup session is pollable — use the Agent strategy endpoint then."},"assistantSessionId":{"type":"string","nullable":true,"description":"Newest assistant session linked to this workflow, regardless of status. Null if no assistant session has been created for this workflow."},"assistantThreadId":{"type":"string","nullable":true,"description":"Newest assistant thread within the assistant session."},"assistantEligible":{"type":"boolean","description":"True when this workflow's lane supports the assistant (SHELLY_SCRIPT or SHELLY_REAL_TIME_SCRIPT). Independent of assistantSessionId; combine with !assistantSessionId for start-vs-continue."},"assistantState":{"$ref":"#/components/schemas/WorkflowAssistantState"},"presentation":{"$ref":"#/components/schemas/WorkflowPresentation"},"execution":{"$ref":"#/components/schemas/WorkflowExecutionState"},"availableActions":{"$ref":"#/components/schemas/WorkflowAvailableActions"},"workspaceActivity":{"type":"string","enum":["idle","assistant","repair"],"description":"Current workspace execution lane, independent of preview readiness."},"assistantFinishedAt":{"type":"string","format":"date-time","nullable":true},"sessionStatus":{"type":"string","nullable":true,"enum":["pending","active","idle","inactive","failed","interrupted","errored","aborted","timed_out"],"description":"Low-level status of the latest Assistant conversation. Use it only to decide whether that conversation can accept input. Do not infer workflow progress or whether a reply is needed; use displayState and awaitingUserInput instead."},"awaitingUserInput":{"type":"object","nullable":true,"description":"Present when the workflow cannot progress without the requesting user's next input. Scoped to that user; do not infer this from sessionStatus.","required":["since"],"properties":{"since":{"type":"string","format":"date-time","description":"When the workflow began waiting for user input"},"prompt":{"type":"string","description":"The assistant's explicit question, when it paused on one"}}}}}}}},"400":{"description":"Bad Request - Invalid workflowId format"},"401":{"description":"Unauthorized - Invalid or missing authentication token"},"403":{"description":"Forbidden - User doesn't have required permissions"},"404":{"description":"Workflow not found"},"500":{"description":"Internal server error"}},"description":"Retrieves detailed information about a specific workflow. This endpoint requires authentication and proper\nteam access permissions.\n"},"delete":{"summary":"Delete a workflow","tags":["Workflows"],"parameters":[{"name":"workflowId","in":"path","required":true,"description":"The ID of the workflow to delete","schema":{"type":"string"}}],"security":[{"ApiKeyAuth":[]}],"responses":{"200":{"description":"Workflow deleted successfully","content":{"text/plain":{"schema":{"type":"string","example":"Workflow deleted"}}}},"401":{"description":"x-api-key missing or not authorized"}}}},"/v4/workflows/{workflowId}/compliance-approve":{"put":{"summary":"Approve workflow for compliance","tags":["Workflows"],"parameters":[{"name":"x-api-key","in":"header","required":false,"description":"API key for authorization","schema":{"type":"string"}},{"name":"Authorization","in":"header","required":false,"description":"Bearer token for authorization","schema":{"type":"string"}},{"name":"workflowId","in":"path","required":true,"description":"ID of the workflow to approve","schema":{"type":"string"}}],"security":[{"ApiKeyAuth":[]}],"responses":{"200":{"description":"Workflow approved successfully","content":{"application/json":{"schema":{"type":"object","properties":{"success":{"type":"boolean"},"message":{"type":"string"},"workflowId":{"type":"string"},"newState":{"type":"string","enum":["QUEUED"]},"actionBy":{"type":"string"},"actionAt":{"type":"string"}}}}}},"400":{"description":"Bad request - workflow not in compliance review state"},"403":{"description":"Forbidden - requires COMPLIANCE_OFFICER role (no exceptions for admin/owner)"},"404":{"description":"Workflow not found"},"500":{"description":"Internal server error"}}}},"/v4/workflows/{workflowId}/compliance-reject":{"put":{"summary":"Reject workflow for compliance","tags":["Workflows"],"parameters":[{"name":"x-api-key","in":"header","required":false,"description":"API key for authorization","schema":{"type":"string"}},{"name":"Authorization","in":"header","required":false,"description":"Bearer token for authorization","schema":{"type":"string"}},{"name":"workflowId","in":"path","required":true,"description":"ID of the workflow to reject","schema":{"type":"string"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["reason"],"properties":{"reason":{"type":"string","description":"Reason for rejecting the workflow","example":"Workflow violates data privacy policies"}}}}}},"security":[{"ApiKeyAuth":[]}],"responses":{"200":{"description":"Workflow rejected successfully","content":{"application/json":{"schema":{"type":"object","properties":{"success":{"type":"boolean"},"message":{"type":"string"},"workflowId":{"type":"string"},"newState":{"type":"string","enum":["COMPLIANCE_REJECTED"]},"actionBy":{"type":"string"},"actionAt":{"type":"string"}}}}}},"400":{"description":"Bad request - workflow not in compliance review state or missing reason"},"403":{"description":"Forbidden - requires COMPLIANCE_OFFICER role (no exceptions for admin/owner)"},"404":{"description":"Workflow not found"},"500":{"description":"Internal server error"}}}},"/v4/workflows/{workflowId}/connectors":{"get":{"summary":"List destinations delivering this workflow's results","description":"Returns the team's destinations that deliver this workflow after each run. Only deliverable destinations are listed (enabled, verified, not revoked).","tags":["Workflows"],"parameters":[{"name":"workflowId","in":"path","required":true,"description":"The ID of the workflow","schema":{"type":"string"}}],"security":[{"ApiKeyAuth":[]}],"responses":{"200":{"description":"Destinations delivering this workflow","content":{"application/json":{"schema":{"type":"object","properties":{"connectors":{"type":"array","items":{"type":"object","properties":{"name":{"type":"string"},"provider":{"type":"string","enum":["s3","gcs","snowflake","databricks","sftp"]},"destination":{"type":"string","description":"Display-safe delivery destination (bucket URI, SFTP host, warehouse share). Contains no credentials."},"formats":{"type":"array","items":{"type":"string"}}}}}}}}}},"401":{"description":"Unauthorized"},"404":{"description":"Workflow not found"}}}},"/v4/workflows/{workflowId}/data":{"get":{"summary":"Get workflow data by ID","tags":["Workflows"],"parameters":[{"name":"x-api-key","in":"header","required":false,"description":"API key for authorization","schema":{"type":"string"}},{"name":"Authorization","in":"header","required":false,"description":"Bearer token for authorization","schema":{"type":"string"}},{"name":"workflowId","in":"path","required":true,"description":"ID of the workflow to retrieve data from","schema":{"type":"string"}},{"name":"runId","in":"query","required":false,"description":"ID of a specific run to retrieve data from","schema":{"type":"string"}},{"name":"format","in":"query","required":false,"description":"Format of the response data","schema":{"type":"string","enum":["json","csv"],"default":"json"}},{"name":"sortBy","in":"query","required":false,"description":"Field to sort the results by","schema":{"type":"string"}},{"name":"order","in":"query","required":false,"description":"Sort order (ascending or descending)","schema":{"type":"string","enum":["asc","desc"],"default":"asc"}},{"name":"filters","in":"query","required":false,"description":"JSON-encoded array of filter objects","schema":{"type":"string"},"example":"[{\"field\":\"jobTitle\",\"operator\":\"CONTAINS\",\"value\":\"Manager\"},{\"field\":\"postedDate\",\"operator\":\"GREATER_THAN\",\"value\":\"2023-01-01\"}]"},{"name":"page","in":"query","required":false,"description":"Page number for pagination","schema":{"type":"integer","minimum":1,"default":1}},{"name":"limit","in":"query","required":false,"description":"Number of items per page (0 for streaming all data)","schema":{"type":"integer","minimum":0,"default":25}},{"name":"gzip","in":"query","required":false,"description":"Enable gzip compression for the response","schema":{"type":"boolean","default":false}},{"name":"rowIds","in":"query","required":false,"description":"Filter results by specific row IDs (comma-separated or JSON array)","schema":{"type":"string"},"example":"id1,id2,id3"},{"name":"download","in":"query","required":false,"description":"\"stream\" (default) returns the data inline (subject to a 5-minute response timeout).\n\"link\" materializes the full result set as a CSV in object storage and returns a JSON\nbody with an export id; the caller then streams the file from\nGET /v4/workflows/{workflowId}/data/exports/{exportId}. Use \"link\" for large exports\nthat would exceed the streaming timeout. Currently requires format=csv.\n","schema":{"type":"string","enum":["stream","link"],"default":"stream"}}],"security":[{"ApiKeyAuth":[]},{"BearerAuth":[]}],"responses":{"200":{"description":"Workflow data returned successfully. The application/json body has two shapes:\nthe default streaming shape (workflowId, data, pagination), and the download=link\nshape (export id pointing at a materialized CSV; fetch via the exports endpoint).\n","content":{"application/json":{"schema":{"oneOf":[{"type":"object","description":"Default streaming response (download omitted or download=stream).","required":["workflowId","data","pagination"],"properties":{"workflowId":{"type":"string"},"runId":{"type":"string","nullable":true},"executedAt":{"type":"string","format":"date-time","nullable":true},"data":{"type":"array","items":{"type":"object"}},"pagination":{"type":"object","properties":{"totalCount":{"type":"integer"},"page":{"type":"integer"},"totalPages":{"type":"integer"},"limit":{"type":"integer"}}}}},{"type":"object","description":"Returned when download=link. The CSV is materialized to object storage and fetched via GET /v4/workflows/{workflowId}/data/exports/{exportId}.","required":["workflowId","format","totalRows","exportId","downloadPath","expiresAt"],"properties":{"workflowId":{"type":"string"},"runId":{"type":"string","nullable":true},"executedAt":{"type":"string","format":"date-time","nullable":true},"format":{"type":"string","enum":["csv"]},"totalRows":{"type":"integer"},"exportId":{"type":"string","format":"uuid","description":"Identifier of the materialized CSV. Pass to the exports endpoint to download."},"downloadPath":{"type":"string","description":"Authenticated download path; combine with the API base URL."},"expiresAt":{"type":"string","format":"date-time"}}}]}},"text/csv":{"schema":{"type":"string"}}}},"400":{"description":"Bad request (invalid parameters)"},"401":{"description":"Unauthorized (invalid or missing API key or Bearer token)"},"404":{"description":"Workflow or job not found"},"409":{"description":"No run is published for a download, or the producing run schema is unavailable","content":{"application/json":{"schema":{"type":"object","required":["code","error"],"properties":{"code":{"type":"string","enum":["DATA_NOT_PUBLISHED","PRODUCING_SCHEMA_UNAVAILABLE"]},"error":{"type":"string"},"runId":{"type":"string"}}}}}},"500":{"description":"Internal server error"}},"x-filter-options":{"description":"The 'filters' parameter accepts a JSON-encoded array of filter objects. Each filter object should have the following structure:\n\n{\n  \"field\": \"fieldName\",\n  \"operator\": \"OPERATOR\",\n  \"value\": \"filterValue\"\n}\n\nAvailable operators:\n- EQUALS: Exact match\n- NOT_EQUALS: Does not match\n- CONTAINS: Field contains the value (case-insensitive)\n- NOT_CONTAINS: Field does not contain the value (case-insensitive)\n- STARTS_WITH: Field starts with the value (case-insensitive)\n- ENDS_WITH: Field ends with the value (case-insensitive)\n- GREATER_THAN: Field is greater than the value\n- LESS_THAN: Field is less than the value\n- GREATER_THAN_OR_EQUAL: Field is greater than or equal to the value\n- LESS_THAN_OR_EQUAL: Field is less than or equal to the value\n- IN: Field value is in the provided array\n- NOT_IN: Field value is not in the provided array\n- IS_NULL: Field is null\n- IS_NOT_NULL: Field is not null\n- IS_EMPTY: Field is null or an empty string\n- IS_NOT_EMPTY: Field is not null and not an empty string\n- BEFORE: Field date is before the specified date (for date fields)\n- AFTER: Field date is after the specified date (for date fields)\n- WITHIN_LAST_DAYS: Field date is within the last N days (value should be a positive integer)\n\nExample:\n[\n  {\"field\": \"jobTitle\", \"operator\": \"CONTAINS\", \"value\": \"Manager\"},\n  {\"field\": \"postedDate\", \"operator\": \"GREATER_THAN\", \"value\": \"2023-01-01\"},\n  {\"field\": \"department\", \"operator\": \"IN\", \"value\": [\"Sales\", \"Marketing\"]}\n]\n"},"x-code-samples":[{"lang":"curl","source":"curl -X GET \"https://api.kadoa.com/v4/workflows/123456789/data?format=json&sortBy=postedDate&order=desc&filters=%5B%7B%22field%22%3A%22jobTitle%22%2C%22operator%22%3A%22CONTAINS%22%2C%22value%22%3A%22Manager%22%7D%2C%7B%22field%22%3A%22postedDate%22%2C%22operator%22%3A%22GREATER_THAN%22%2C%22value%22%3A%222023-01-01%22%7D%5D&page=1&limit=25\" \\\n-H \"x-api-key: YOUR_API_KEY\"\n"},{"lang":"python","source":"import requests\nimport json\n\nurl = \"https://api.kadoa.com/v4/workflows/123456789/data\"\nheaders = {\n    \"x-api-key\": \"YOUR_API_KEY\"\n}\nparams = {\n    \"format\": \"json\",\n    \"sortBy\": \"postedDate\",\n    \"order\": \"desc\",\n    \"filters\": json.dumps([\n        {\"field\": \"jobTitle\", \"operator\": \"CONTAINS\", \"value\": \"Manager\"},\n        {\"field\": \"postedDate\", \"operator\": \"GREATER_THAN\", \"value\": \"2023-01-01\"}\n    ]),\n    \"page\": 1,\n    \"limit\": 25\n}\n\nresponse = requests.get(url, headers=headers, params=params)\ndata = response.json()\nprint(data)\n"}]}},"/v4/workflows/{workflowId}/data/export":{"get":{"summary":"Create workflow data export","description":"Materializes the full result set as CSV, JSON, or Parquet to object storage and returns a self-authenticating\nURL that can be opened by external clients (Claude Desktop, Claude for Excel, code execution sandboxes,\nbrowsers) without an Authorization header. The URL is HMAC-signed and bound to the exportId, workflowId,\nformat and expiry.\n","tags":["Workflows"],"security":[{"ApiKeyAuth":[]},{"BearerAuth":[]}],"parameters":[{"name":"workflowId","in":"path","required":true,"schema":{"type":"string"}},{"name":"format","in":"query","required":false,"schema":{"type":"string","enum":["csv","json","parquet"],"default":"csv"}},{"name":"runId","in":"query","required":false,"schema":{"type":"string"}},{"name":"filters","in":"query","required":false,"schema":{"type":"string"}},{"name":"sortBy","in":"query","required":false,"schema":{"type":"string"}},{"name":"order","in":"query","required":false,"schema":{"type":"string","enum":["asc","desc"],"default":"asc"}},{"name":"rowIds","in":"query","required":false,"schema":{"type":"string"}}],"responses":{"200":{"description":"Export materialized","content":{"application/json":{"schema":{"type":"object","required":["workflowId","runId","format","rowCount","url","expiresAt"],"properties":{"workflowId":{"type":"string"},"runId":{"type":"string"},"executedAt":{"type":"string","format":"date-time"},"format":{"type":"string","enum":["csv","json","parquet"]},"rowCount":{"type":"integer"},"url":{"type":"string","description":"Signed, self-authenticating download URL. Valid until expiresAt."},"expiresAt":{"type":"string","format":"date-time"}}}}}},"400":{"description":"Invalid query params"},"401":{"description":"Unauthorized"},"404":{"description":"Workflow or run not found"},"409":{"description":"No workflow run is published, or the producing run schema is unavailable","content":{"application/json":{"schema":{"type":"object","required":["code","error"],"properties":{"code":{"type":"string","enum":["DATA_NOT_PUBLISHED","PRODUCING_SCHEMA_UNAVAILABLE"]},"error":{"type":"string"},"runId":{"type":"string"}}}}}}}}},"/v4/workflows/{workflowId}/data/parquet":{"get":{"summary":"Workflow data Parquet option","description":"Streams the canonical Parquet artifact for the latest successful workflow run, or for a\nspecific run when `runId` is provided. The file is the full, unfiltered dataset for that run.\nUse this endpoint for typed analytical ingestion into engines such as DuckDB, Spark, Polars,\nSnowflake, or BigQuery.\n","tags":["Workflows"],"security":[{"ApiKeyAuth":[]},{"BearerAuth":[]}],"parameters":[{"name":"workflowId","in":"path","required":true,"description":"ID of the workflow whose Parquet data should be downloaded.","schema":{"type":"string"}},{"name":"runId","in":"query","required":false,"description":"Optional workflow run ID. Omit to download the latest successful run.","schema":{"type":"string"}}],"responses":{"200":{"description":"Parquet file bytes.","content":{"application/vnd.apache.parquet":{"schema":{"type":"string","format":"binary"}}}},"400":{"description":"Invalid workflowId or runId."},"401":{"description":"Unauthorized."},"404":{"description":"Workflow, run, or Parquet artifact not found."},"500":{"description":"Internal server error."}}}},"/v4/workflows/{workflowId}/data/exports/{exportId}":{"get":{"summary":"Download workflow data export","description":"Streams a file previously materialized via GET /v4/workflows/{workflowId}/data/export.\nSets Content-Disposition: attachment so browsers trigger a download.\n","tags":["Workflows"],"security":[{"ApiKeyAuth":[]},{"BearerAuth":[]}],"parameters":[{"name":"workflowId","in":"path","required":true,"schema":{"type":"string"}},{"name":"exportId","in":"path","required":true,"description":"Export id returned by the export response.","schema":{"type":"string","format":"uuid"}}],"responses":{"200":{"description":"Export bytes","content":{"text/csv":{"schema":{"type":"string"}},"application/json":{"schema":{"type":"string"}},"application/vnd.apache.parquet":{"schema":{"type":"string","format":"binary"}}}},"400":{"description":"Invalid workflowId or exportId"},"401":{"description":"Unauthorized"},"404":{"description":"Workflow or export not found"}}}},"/v4/workflows/{workflowId}/history/metrics":{"get":{"summary":"Get aggregated run success metrics for a workflow","description":"Per-day successful/failed run counts and the overall success rate over the requested window, aggregated over all runs (not paginated). Days are bucketed by the run's finish date in UTC.","tags":["Workflows"],"security":[{"ApiKeyAuth":[]}],"parameters":[{"in":"path","name":"workflowId","required":true,"schema":{"type":"string"},"description":"The unique identifier of the workflow"},{"in":"query","name":"days","required":false,"schema":{"type":"integer","minimum":1,"maximum":90,"default":30},"description":"Number of calendar days (UTC) covered by the window, from midnight days-1 days ago through now"}],"responses":{"200":{"description":"Aggregated run metrics for the workflow","content":{"application/json":{"schema":{"type":"object","properties":{"workflowId":{"type":"string","description":"Unique identifier of the workflow"},"windowStart":{"type":"string","format":"date-time","description":"Inclusive start of the aggregation window"},"windowEnd":{"type":"string","format":"date-time","description":"Exclusive end of the aggregation window"},"totalRuns":{"type":"integer","description":"Number of terminal (finished or failed) runs in the window"},"successfulRuns":{"type":"integer","description":"Number of finished runs in the window"},"failedRuns":{"type":"integer","description":"Number of failed runs in the window"},"successRatePercentage":{"type":"number","nullable":true,"description":"successfulRuns / totalRuns as a percentage, null when the window has no terminal runs"},"daily":{"type":"array","description":"Per-day buckets (UTC, by run finish date); days without terminal runs are omitted","items":{"type":"object","properties":{"date":{"type":"string","format":"date","description":"UTC calendar day of the bucket"},"successfulRuns":{"type":"integer"},"failedRuns":{"type":"integer"},"uptimePercentage":{"type":"number","description":"successfulRuns / (successfulRuns + failedRuns) for the day as a percentage"}}}}}}}}},"400":{"description":"Invalid workflow ID or days parameter"},"401":{"description":"Unauthorized access, either due to missing or invalid x-api-key"},"404":{"description":"Workflow with the specified ID could not be found"},"500":{"description":"Internal server error"}}}},"/v4/workflows/{workflowId}/history":{"get":{"summary":"Get the workflow run history","tags":["Workflows"],"security":[{"ApiKeyAuth":[]}],"parameters":[{"in":"path","name":"workflowId","required":true,"schema":{"type":"string"},"description":"The unique identifier of the workflow whose runs history is to be retrieved"},{"in":"query","name":"page","required":false,"schema":{"type":"integer","default":1},"description":"Page number, 1-based (default 1)"},{"in":"query","name":"limit","required":false,"schema":{"type":"integer","default":25},"description":"Maximum number of runs per page (default 25, min 1, max 1000)"},{"in":"query","name":"runId","schema":{"type":"string"},"description":"Look up one run belonging to this workflow, independently of pagination"},{"in":"query","name":"status","required":false,"schema":{"type":"string","enum":["success","failed","in_progress"]},"description":"Filter runs by outcome. success maps to FINISHED, failed maps to FAILED, in_progress maps to RUNNING."}],"responses":{"200":{"description":"History of workflow runs","content":{"application/json":{"schema":{"type":"object","properties":{"workflowId":{"type":"string","description":"Unique identifier of the workflow"},"workflowRuns":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string","description":"Unique identifier of the workflow run"},"state":{"type":"string","enum":["IN_PROGRESS","VALIDATING","FINISHED","FAILED","NOT_SUPPORTED","FAILED_INSUFFICIENT_FUNDS"],"description":"State of the workflow run. VALIDATING means the run finished extracting but is held for QA review before data is delivered."},"startedAt":{"type":"string","format":"date-time","description":"Start date and time of the workflow run"},"finishedAt":{"type":"string","format":"date-time","description":"Finish date and time of the workflow run"},"screenshot":{"type":"string","description":"Screenshot of the navigation during the workflow run"},"records":{"type":"integer","description":"Number of records processed in the workflow run"},"errors":{"type":"array","description":"Errors that occurred during the workflow run","items":{"type":"object","properties":{"errorCode":{"type":"string","description":"Error code identifying the type of error"},"message":{"type":"string","description":"Human-readable error message"},"timestamp":{"type":"string","format":"date-time","description":"When the error occurred"},"screenshot":{"type":"string","description":"Optional screenshot URL"},"context":{"type":"object","description":"Additional context about the error","properties":{"url":{"type":"string","description":"The URL where the error occurred"},"httpStatus":{"type":"integer","description":"HTTP status code if applicable"},"retryCount":{"type":"integer","description":"Number of retry attempts made"},"details":{"type":"string","description":"Additional error-specific details"},"timestamp":{"type":"string","format":"date-time","description":"When the error context was captured"}},"additionalProperties":true}}}},"startedBy":{"type":"string","nullable":true,"enum":["SCHEDULE","DASHBOARD","API","WORKFLOW_TRIGGER","ASSISTANT","KADOA"],"description":"What started the run. API covers the API, SDKs, MCP, and CLI. KADOA means Kadoa started it. Null when the origin was not recorded."}}}},"totalCount":{"type":"integer","description":"Total number of workflow runs matching the query (across all pages)"},"pagination":{"type":"object","properties":{"page":{"type":"integer","description":"Current page number"},"limit":{"type":"integer","description":"Maximum number of items per page"},"totalPages":{"type":"integer","description":"Total number of pages"},"totalCount":{"type":"integer","description":"Total number of workflow runs matching the query"}}}}}}}},"401":{"description":"Unauthorized access, either due to missing or invalid x-api-key"},"404":{"description":"Workflow with the specified ID could not be found"}}}},"/v4/workflows":{"post":{"description":"Create a workflow from natural-language instructions, an existing schema, an inline schema, raw-data output options, or a published template.","summary":"Create a new workflow","tags":["Workflows"],"parameters":[],"requestBody":{"description":"Body","content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateWorkflowBody"}}}},"responses":{"201":{"description":"201","content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateWorkflowResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"oneOf":[{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]},{"$ref":"#/components/schemas/TemplateControlledFieldError"}]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"403":{"description":"403","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"422":{"description":"422","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SourcesMultipleSitesError"}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"503":{"description":"503","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]},"get":{"summary":"Get a list of workflows","description":"Retrieves a list of workflows with pagination and search capabilities","tags":["Workflows"],"security":[{"ApiKeyAuth":[]}],"parameters":[{"name":"search","in":"query","description":"Search term to filter workflows by name or workflow ID","required":false,"schema":{"type":"string"}},{"name":"skip","in":"query","description":"Number of items to skip","required":false,"schema":{"type":"integer","minimum":0,"default":0}},{"name":"limit","in":"query","description":"Maximum number of items to return","required":false,"schema":{"type":"integer","minimum":1,"default":25}},{"name":"state","in":"query","description":"Filter by the persisted state of the long-lived workflow. Use displayState for its computed operational status, statusFilters for dashboard categories, and inSupport for support ownership. DRAFT workflows are excluded by default unless explicitly requested.","required":false,"schema":{"type":"string","enum":["ACTIVE","DRAFT","PAUSED","PREVIEW","QUEUED","SETUP","COMPLIANCE_REVIEW","COMPLIANCE_REJECTED","NOT_SUPPORTED","ERROR","DELETED"]}},{"name":"runState","in":"query","description":"Filter by the latest execution attempt. Use this for run diagnostics, not workflow status UI.","required":false,"schema":{"type":"string","enum":["FAILED","FINISHED","RUNNING","STOPPED"]}},{"name":"displayState","in":"query","description":"Filter by the workflow's computed operational state. This does not include pending user input or support ownership; use statusFilters for those dashboard categories. Accepts comma-separated values.","required":false,"schema":{"type":"string","enum":["ACTIVE","DRAFT","PAUSED","PREVIEW","FAILED","RUNNING","VALIDATING","PENDING_START","COMPLIANCE_REVIEW","COMPLIANCE_REJECTED"]}},{"name":"inSupport","in":"query","description":"Filter workflows by support status (has open support request)","required":false,"schema":{"type":"string","enum":[true,false]}},{"name":"tags","in":"query","description":"Filter workflows by tags. Accepts repeated params, comma-separated values, or a JSON array.","required":false,"schema":{"type":"array","items":{"type":"string"}}},{"name":"statusFilters","in":"query","description":"Filter by dashboard category. group:attention returns the workflows shown under \"Needs your attention\" in the dashboard, which is where the requesting user must reply to the Assistant or approve preview data. Accepts repeated params, comma-separated values, or a JSON array. The API also accepts dashboard-internal composite values sent by the Kadoa dashboard; those are not part of the public contract and may change.","required":false,"schema":{"type":"array","items":{"type":"string","enum":["group:attention","group:working","group:support","group:failed","group:active","group:complete","group:paused"]}}},{"name":"view","in":"query","description":"Use dashboard for a compact list without schema, notificationConfig, additionalData, or monitored_fields. Includes summaryOnly, hasPrompt, and hasSchema flags. Omit for the full list representation. CSV exports are unchanged.","required":false,"schema":{"type":"string","enum":["dashboard"]}},{"name":"groupWindows","in":"query","description":"Dashboard-only grouped list mode. JSON object mapping expanded dashboard groups to an offset and batch limit. Omitted groups return counts but no workflow rows. The response includes groupPagination. Besides the status groups, the \"pinned\" group holds the workflows the requesting user pinned, whatever their status.","required":false,"schema":{"type":"string"}},{"name":"userId","in":"query","description":"Filter workflows by one or more user IDs. Accepts repeated params, comma-separated values, or a JSON array.","required":false,"schema":{"type":"array","items":{"type":"string"}}},{"name":"channelId","in":"query","description":"Filter workflows by one or more notification channel IDs. Accepts repeated params, comma-separated values, or a JSON array.","required":false,"schema":{"type":"array","items":{"type":"string"}}},{"name":"monitoring","in":"query","description":"Filter workflows by monitoring status","required":false,"schema":{"type":"string","enum":["true","false"]}},{"name":"updateInterval","in":"query","description":"Filter workflows by update interval. REAL_TIME matches workflows that run in real time, independent of notification configuration.","required":false,"schema":{"type":"string","enum":["HOURLY","DAILY","WEEKLY","MONTHLY","REAL_TIME"]}},{"name":"scheduleType","in":"query","description":"Filter workflows by schedule type. RUN_ONCE = no recurring schedule (Complete), RECURRING = has a recurring/real-time schedule (Scheduled).","required":false,"schema":{"type":"string","enum":["RUN_ONCE","RECURRING"]}},{"name":"templateId","in":"query","description":"Filter to workflows instantiated from one or more template IDs. Accepts repeated params, comma-separated values, or a JSON array.","required":false,"schema":{"type":"array","items":{"type":"string"}}},{"name":"includeDeleted","in":"query","description":"Include deleted workflows (for compliance officers)","required":false,"schema":{"type":"string","enum":[true,false],"default":false}},{"name":"format","in":"query","description":"Response format (json or csv for export)","required":false,"schema":{"type":"string","enum":["json","csv"],"default":"json"}}],"responses":{"200":{"description":"Successfully retrieved workflows","content":{"application/json":{"schema":{"type":"object","properties":{"workflows":{"type":"array","description":"List of workflows","items":{"type":"object","properties":{"id":{"type":"string","description":"Unique identifier for the workflow"},"name":{"type":"string","description":"Name of the workflow"},"description":{"type":"string","description":"Description of the workflow"},"state":{"type":"string","enum":["ACTIVE","DRAFT","ERROR","PAUSED","NOT_SUPPORTED","PREVIEW","COMPLIANCE_REVIEW","COMPLIANCE_REJECTED","QUEUED","SETUP","DELETED"],"description":"Persisted state of the long-lived workflow. It may describe setup or a control state such as ACTIVE or PAUSED. Use displayState for operational status UI."},"displayState":{"type":"string","enum":["ACTIVE","DRAFT","ERROR","PAUSED","NOT_SUPPORTED","PREVIEW","QUEUED","SETUP","PENDING_START","RUNNING","VALIDATING","FAILED","DEGRADED","COMPLIANCE_REVIEW","COMPLIANCE_REJECTED","DELETED","STOPPED"],"description":"Computed operational summary based on workflow state, the latest run, and monitor health. It does not indicate pending user input or support ownership; use awaitingUserInput and inSupport for those. ACTIVE may be presented as Complete, Scheduled, or Running depending on workflow type and schedule."},"reviewReason":{"type":"string","enum":["COMPLIANCE_REVIEW","HARD_FAIL","TRANSFORMATION_REPAIR_REQUIRED","MINIMUM_HUMAN_APPROVALS","DATA_QUALITY_SCHEMA_ADHERENCE","DATA_QUALITY_SCHEMA_VALIDATION","DATA_QUALITY_COMPLETENESS","DATA_QUALITY_SEMANTIC_PLAUSIBILITY","ROW_COUNT_CHANGED","WORKFLOW_REVISION_DRIFT","ZERO_RESULTS"],"description":"Why the latest run is being verified. Only present while displayState is VALIDATING."},"openSupportRequests":{"type":"array","description":"List of open support requests for this workflow. Only present when there are open requests.","items":{"type":"object","properties":{"issueId":{"type":"string","nullable":true,"description":"Linear issue identifier (e.g., KAD-123)"},"requestedAt":{"type":"string","format":"date-time","description":"When the support request was created"},"status":{"type":"string","description":"Customer-visible ticket status synced from Linear (e.g., In Progress). Absent until the first sync."},"statusType":{"type":"string","description":"Status category backing `status` (e.g., unstarted, started, completed)"}}}},"inSupport":{"type":"boolean","description":"True when Kadoa support has an open ticket on this workflow. Same predicate as the inSupport query filter. Independent of state/displayState: this answers who is handling the workflow, while displayState answers whether it is delivering data. Prefer this over recomputing from openSupportRequests."},"awaitingUserInput":{"type":"object","nullable":true,"description":"Present when the workflow cannot progress without the requesting user's next input. Scoped to that user; do not infer this from sessionStatus.","required":["since"],"properties":{"since":{"type":"string","format":"date-time","description":"When the workflow began waiting for user input"},"prompt":{"type":"string","description":"The assistant's explicit question, when it paused on one"}}},"userId":{"type":"string","description":"ID of the user who owns the workflow"},"userName":{"type":"string","description":"Display name of the workflow owner"},"userEmail":{"type":"string","format":"email","description":"Email of the workflow owner"},"createdAt":{"type":"string","format":"date-time","description":"Timestamp when the workflow was created"},"updateInterval":{"type":"string","description":"Update frequency"},"isRealTime":{"type":"boolean","description":"Whether this workflow should be displayed as realtime"},"lastDataChangedAt":{"type":"string","format":"date-time","nullable":true,"description":"Most recent persisted customer-visible data change for a real-time workflow"},"assistantEligible":{"type":"boolean","description":"Whether this workflow mode supports the workflow Assistant."},"assistantSessionId":{"type":"string","nullable":true,"description":"Most recent customer-facing Assistant session linked to this workflow."},"assistantThreadId":{"type":"string","nullable":true,"description":"Most recent customer-facing Assistant thread within assistantSessionId."},"assistantState":{"$ref":"#/components/schemas/WorkflowAssistantState"},"presentation":{"$ref":"#/components/schemas/WorkflowPresentation"},"execution":{"$ref":"#/components/schemas/WorkflowExecutionState"},"availableActions":{"$ref":"#/components/schemas/WorkflowAvailableActions"},"workspaceActivity":{"type":"string","enum":["idle","assistant","repair"],"description":"Current workspace execution lane, independent of preview readiness."},"assistantFinishedAt":{"type":"string","format":"date-time","nullable":true},"sessionStatus":{"type":"string","nullable":true,"enum":["pending","created","active","idle","inactive","failed","interrupted","errored","aborted","timed_out"],"description":"Current status of the listed customer-facing Assistant session."},"tags":{"type":"array","items":{"type":"string"},"description":"Tags associated with the workflow"},"limit":{"type":"integer","description":"Maximum number of items to scrape"},"finishedAt":{"type":"string","format":"date-time","description":"When the last job finished"},"startedAt":{"type":"string","format":"date-time","description":"When the last job started"},"estimatedFinishedAtUtc":{"type":"string","format":"date-time","nullable":true,"description":"Estimated UTC finish time for the active job, when available."},"jobId":{"type":"string","description":"ID of the latest operational run attempt"},"publishedJobId":{"type":"string","description":"ID of the latest finished run that supplies customer-visible data"},"dataKey":{"type":"string","description":"Database key for the workflow data"},"location":{"type":"object","properties":{"type":{"type":"string","enum":["auto","manual"]},"isoCode":{"type":"string","enum":["DE","US","GB","NL","CA"]}},"description":"Scraping location configuration"},"runState":{"type":"string","enum":["RUNNING","FINISHED","FAILED","STOPPED"],"description":"State of the latest execution attempt. Use this for run diagnostics or workflow history, not as the workflow lifecycle or status label."},"templateId":{"type":"string","nullable":true,"description":"Linked workflow template identifier."},"templateVersion":{"type":"integer","nullable":true,"description":"Version pinned to the workflow's template linkage."},"templateLatestVersion":{"type":"integer","nullable":true,"description":"Most recent published version of the linked template."},"templateIsOutdated":{"type":"boolean","description":"Whether a newer template version exists than the workflow's pinned version."},"totalRecords":{"type":"integer","description":"Total number of records extracted"},"url":{"type":"string","description":"Primary URL being scraped"},"urls":{"type":"array","items":{"type":"string"},"description":"List of URLs being scraped"},"browserActions":{"type":"array","description":"Optional browser actions to perform before extraction","items":{"type":"object","properties":{"type":{"type":"string","description":"Action type (e.g., CLICK, TYPE, WAIT, GOTO)"},"selector":{"type":"string","description":"CSS selector for element-based actions"},"text":{"type":"string","description":"Text to type for TYPE actions"},"timeMs":{"type":"integer","description":"Milliseconds to wait for WAIT actions"},"url":{"type":"string","description":"URL to navigate to for GOTO actions"}}}},"schema":{"type":"array","items":{"type":"object","properties":{"name":{"type":"string"},"description":{"type":"string"},"example":{"type":"string"},"dataType":{"type":"string","enum":["STRING","NUMBER","BOOLEAN","DATE","DATETIME","CURRENCY","MONEY","IMAGE","LINK","OBJECT","ARRAY"]},"isKey":{"type":"boolean"},"isRequired":{"type":"boolean"},"isUnique":{"type":"boolean"}}},"description":"Extraction schema fields"},"schemaName":{"type":"string","description":"Name of the schema used"},"schemaId":{"type":"string","description":"ID of the schema used"},"errors":{"type":"array","description":"Errors from the last job run","items":{"type":"object","properties":{"errorCode":{"type":"string","description":"Error code identifying the type of error"},"message":{"type":"string","description":"Human-readable error message"},"timestamp":{"type":"string","format":"date-time","description":"When the error occurred"},"screenshot":{"type":"string","description":"Optional screenshot URL"},"context":{"type":"object","description":"Additional context about the error","properties":{"url":{"type":"string","description":"The URL where the error occurred"},"httpStatus":{"type":"integer","description":"HTTP status code if applicable"},"retryCount":{"type":"integer","description":"Number of retry attempts made"},"details":{"type":"string","description":"Additional error-specific details"},"timestamp":{"type":"string","format":"date-time","description":"When the error context was captured"}},"additionalProperties":true}}}},"monitoring":{"type":"boolean","description":"Whether monitoring is enabled"},"notificationConfig":{"type":"object","properties":{"enabled":{"type":"boolean"},"fields":{"type":"array","items":{"type":"object","properties":{"fieldName":{"type":"string"},"operator":{"type":"string","enum":["changed","added","removed"]}}}}},"description":"Monitoring configuration"},"observerHealth":{"type":"object","nullable":true,"description":"Health status for monitored workflows. Only present when health monitoring is active and detects issues.","properties":{"healthTier":{"type":"string","enum":["HEALTHY","WARNING","DEGRADED","UNHEALTHY","FAILED"],"description":"Current health tier"},"reason":{"type":"string","description":"Human-readable explanation of the health status"},"issueStartedAt":{"type":"string","format":"date-time","description":"When the current degradation episode started"},"lastCheckedAt":{"type":"string","format":"date-time","description":"When health was last evaluated"}}}}}},"pagination":{"type":"object","description":"Pagination information","properties":{"totalCount":{"type":"integer","description":"Total number of workflows matching the filter criteria"},"page":{"type":"integer","description":"Current page number"},"totalPages":{"type":"integer","description":"Total number of pages"},"limit":{"type":"integer","description":"Number of items per page"}}},"groupPagination":{"type":"object","description":"Per-group counts and window metadata. Present only when groupWindows is requested.","additionalProperties":{"type":"object","properties":{"totalCount":{"type":"integer"},"offset":{"type":"integer"},"returnedCount":{"type":"integer"},"nextOffset":{"type":"integer"},"hasMore":{"type":"boolean"}}}}}}}}},"401":{"description":"Unauthorized - Authentication required"},"403":{"description":"Forbidden - Insufficient permissions"},"500":{"description":"Internal server error"}}}},"/v4/workflows/{workflowId}/metadata":{"put":{"summary":"Update workflow metadata","tags":["Workflows"],"parameters":[{"name":"workflowId","in":"path","required":true,"description":"ID of the workflow to update","schema":{"type":"string"}}],"security":[{"ApiKeyAuth":[]}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"urls":{"type":"array","description":"List of target URLs for the workflow","items":{"type":"string"}},"limit":{"type":"integer","minimum":1,"maximum":2147483647,"nullable":true,"description":"Maximum records per run. Pass null to clear the limit and extract all rows."},"updateInterval":{"type":"string","description":"The new update interval for the workflow","enum":["ONLY_ONCE","EVERY_10_MINUTES","HALF_HOURLY","HOURLY","THREE_HOURLY","SIX_HOURLY","TWELVE_HOURLY","EIGHTEEN_HOURLY","DAILY","TWO_DAY","THREE_DAY","WEEKLY","BIWEEKLY","TRIWEEKLY","FOUR_WEEKS","MONTHLY","CUSTOM"]},"schedules":{"type":"array","items":{"type":"string"},"description":"Array of cron expressions for the workflow schedule"},"timezone":{"type":"string","example":"America/New_York","description":"IANA timezone for cron schedules. A timezone-only update preserves existing cron expressions."},"name":{"type":"string","description":"The new name for the workflow"},"description":{"type":"string","description":"The new description for the workflow"},"tags":{"type":"array","items":{"type":"string"},"description":"The tags for the workflow","example":["tag1","tag2"]},"location":{"type":"object","description":"The new location for the workflow","properties":{"type":{"type":"string","enum":["auto","manual"],"description":"Type of location selection"},"isoCode":{"type":"string","description":"ISO code of the country (required when type is manual)"}}},"monitoring":{"type":"object","required":["fields"],"description":"The monitoring config for the workflow","properties":{"fields":{"type":"array","minItems":1,"items":{"type":"object","required":["fieldName","operator"],"properties":{"fieldName":{"type":"string","minLength":1,"description":"The name of the field to monitor"},"operator":{"type":"string","enum":["changed","added","removed"],"description":"The operator to use for monitoring"},"isKeyField":{"type":"boolean","description":"Optional explicit schema-key update for this field"}}}},"conditions":{"type":"object","required":["logicalOperator","conditions"],"description":"The conditions for monitoring","properties":{"logicalOperator":{"type":"string","enum":["AND","OR"],"description":"The logical operator to use for conditions"},"conditions":{"type":"array","minItems":1,"items":{"type":"object","required":["type","operator"],"properties":{"type":{"type":"string","enum":["SINGLE","ANY"],"description":"Type of condition"},"field":{"type":"string","description":"Field name (required for SINGLE type)"},"operator":{"type":"string","enum":["MATCHES_REGEX","EQUALS","NOT_EQUALS","CONTAINS","NOT_CONTAINS","STARTS_WITH","ENDS_WITH","GREATER_THAN","LESS_THAN","GREATER_THAN_OR_EQUAL","LESS_THAN_OR_EQUAL","IN","NOT_IN","BEFORE","AFTER","WITHIN_LAST_DAYS","IS_NULL","IS_NOT_NULL","IS_EMPTY","IS_NOT_EMPTY"],"description":"Condition operator"},"value":{"oneOf":[{"type":"string"},{"type":"number"},{"type":"boolean"}],"description":"Required except for null/empty operators"}}}}}}}},"entity":{"type":"string","description":"The new entity for the workflow","example":"job_posting"},"schema":{"type":"array","description":"The new extraction schema for the workflow","items":{"type":"object","properties":{"name":{"type":"string"},"description":{"type":"string"},"example":{"type":"string"},"dataType":{"type":"string","enum":["STRING","NUMBER","BOOLEAN","DATE","DATETIME","MONEY","IMAGE","LINK","OBJECT","ARRAY"]},"isPrimaryKey":{"type":"boolean"},"isRequired":{"type":"boolean"},"isUnique":{"type":"boolean"}}}},"additionalData":{"type":"object","description":"Additional static data for the workflow"},"userPrompt":{"type":"string","minLength":10,"maxLength":5000,"description":"Natural language instructions for the workflow."}}}}}},"responses":{"200":{"description":"Workflow metadata updated successfully","content":{"application/json":{"schema":{"type":"object","properties":{"success":{"type":"boolean"},"message":{"type":"string"}}}}}},"400":{"description":"Bad request (invalid input)"},"401":{"description":"Unauthorized"},"404":{"description":"Workflow not found"}}}},"/v4/workflows/{workflowId}/pause":{"put":{"summary":"Pause a workflow","tags":["Workflows"],"parameters":[{"name":"workflowId","in":"path","required":true,"description":"The ID of the workflow to pause","schema":{"type":"string"}}],"security":[{"ApiKeyAuth":[]}],"responses":{"200":{"description":"Workflow paused successfully","content":{"text/plain":{"schema":{"type":"string","example":"Workflow paused"}}}},"401":{"description":"x-api-key missing or not authorized"}}}},"/v4/workflows/{workflowId}/quality-metrics":{"get":{"summary":"Get workflow quality metrics","description":"Returns the data quality metric results for a workflow run, plus the run's total data\nquality issue count.\n\nMetrics are only available once the run has finished, before that the endpoint returns\n`{ \"results\": null, \"issueCount\": null }`.\n\nEach metric result carries a `status`:\n- `OK`: the metric was computed, see `data` for it's details.\n- `PENDING`: the metric has not been computed yet.\n- `NOT_APPLICABLE`: the metric cannot be computed for this workflow, see `message`.\n- `ERROR`: the metric computation failed, see `message`.\n","tags":["Workflows"],"security":[{"ApiKeyAuth":[]},{"BearerAuth":[]}],"parameters":[{"name":"workflowId","in":"path","required":true,"description":"ID of the workflow to retrieve quality metrics for","schema":{"type":"string"}},{"name":"jobId","in":"query","required":false,"description":"ID of a specific published run. Omit to use the latest published run.","schema":{"type":"string"}}],"responses":{"200":{"description":"Quality metric results. `results` and `issueCount` are null until the run has finished.\n","content":{"application/json":{"schema":{"type":"object","required":["results","issueCount"],"properties":{"results":{"type":"object","nullable":true,"description":"Metric results keyed by metric. Null until the run has finished.","properties":{"COMPLETENESS":{"type":"object","description":"Whether the extraction found as many rows as the source suggests.","properties":{"key":{"type":"string","enum":["COMPLETENESS"]},"status":{"type":"string","enum":["OK","PENDING","NOT_APPLICABLE","ERROR"]},"message":{"type":"string","description":"Explanation, present when status is NOT_APPLICABLE or ERROR."},"data":{"type":"object","description":"Metric details, present when status is OK.","properties":{"issueCount":{"type":"integer","description":"Number of issues this metric found. 0 means the metric passed."},"actualRowCount":{"type":"integer","description":"Number of rows the extraction produced."},"expectedRowCount":{"type":"integer","description":"Number of rows the source suggests should exist."},"cappedByLimit":{"type":"boolean","description":"True when the row count was capped by the workflow's extraction limit."},"signals":{"type":"array","description":"Evidence used to derive the expected row count.","items":{"type":"object","properties":{"totalCount":{"type":"integer"},"description":{"type":"string"},"sources":{"type":"array","items":{"type":"object","properties":{"count":{"type":"integer"},"xpath":{"type":"string"},"regex":{"type":"string"},"source":{"type":"string"},"url":{"type":"string"}}}}}}}}}}},"SCHEMA_VALIDATION":{"type":"object","description":"Checks the dataset against the workflow's schema validation rules.","properties":{"key":{"type":"string","enum":["SCHEMA_VALIDATION"]},"status":{"type":"string","enum":["OK","PENDING","NOT_APPLICABLE","ERROR"]},"message":{"type":"string","description":"Explanation, present when status is NOT_APPLICABLE or ERROR."},"data":{"type":"object","description":"Metric details, present when status is OK.","properties":{"issueCount":{"type":"integer","description":"Number of issues this metric found. 0 means the metric passed."},"ruleViolationCount":{"type":"integer","description":"Number of violated rules."},"rowViolationCount":{"type":"integer","description":"Number of rows affected by violations."},"columns":{"type":"array","description":"Per-column validation results.","items":{"type":"object","properties":{"name":{"type":"string"},"rulesConfigured":{"type":"boolean"},"violations":{"type":"array","items":{"type":"object"}}}}}}}}},"SEMANTIC_PLAUSIBILITY":{"type":"object","description":"Flags values that do not fit with the rest of the dataset.","properties":{"key":{"type":"string","enum":["SEMANTIC_PLAUSIBILITY"]},"status":{"type":"string","enum":["OK","PENDING","NOT_APPLICABLE","ERROR"]},"message":{"type":"string","description":"Explanation, present when status is NOT_APPLICABLE or ERROR."},"data":{"type":"object","description":"Metric details, present when status is OK.","properties":{"issueCount":{"type":"integer","description":"Number of issues this metric found. 0 means the metric passed."},"columns":{"type":"array","description":"Per-column plausibility results.","items":{"type":"object","properties":{"name":{"type":"string"},"flaggedPercent":{"type":"number"},"reasoning":{"type":"string"},"flaggedExamples":{"type":"array","items":{"type":"object","properties":{"value":{"type":"string"}}}}}}}}}}}}},"issueCount":{"type":"integer","nullable":true,"description":"Total number of data quality issues detected for the run. Null until the run has finished."}}}}}},"400":{"description":"Invalid workflow ID format"},"401":{"description":"Unauthorized (invalid or missing API key or Bearer token)"},"404":{"description":"Workflow not found"},"500":{"description":"Internal server error"}}}},"/v4/workflows/{workflowId}/resume":{"put":{"summary":"Resume or unpause a workflow","description":"Unpauses a paused workflow, or resumes a preview/error workflow.","tags":["Workflows"],"parameters":[{"name":"workflowId","in":"path","required":true,"description":"The ID of the workflow to resume","schema":{"type":"string"}}],"security":[{"ApiKeyAuth":[]}],"responses":{"200":{"description":"Workflow resumed successfully.","content":{"application/json":{"schema":{"type":"object","properties":{"message":{"type":"string","enum":["Workflow unpaused","Workflow resumed","Workflow unpaused and sent for compliance review","Workflow resumed and sent for compliance review"]}}}}}},"202":{"description":"The preview no longer reflects the current settings, so approving it started a new preview run instead. Approve the new preview once it finishes.","content":{"application/json":{"schema":{"type":"object","properties":{"message":{"type":"string"},"jobId":{"type":"string","description":"The new preview run"}}}}}},"400":{"description":"Cannot resume workflow in current state"},"401":{"description":"x-api-key missing or not authorized"},"403":{"description":"Not authorized"},"404":{"description":"Workflow not found"}}}},"/v4/workflows/{workflowId}/run":{"put":{"summary":"Run a workflow","tags":["Workflows"],"parameters":[{"name":"workflowId","in":"path","required":true,"description":"The ID of the workflow to run","schema":{"type":"string"}}],"requestBody":{"content":{"application/json":{"schema":{"type":"object","properties":{"variables":{"type":"object","description":"Optional variables to pass to the workflow execution","additionalProperties":true},"limit":{"type":"number","description":"Optional limit for the number of records to process","example":100},"preview":{"type":"boolean","description":"Rerun the preview of a PREVIEW-state workflow instead of starting a production run"}}}}}},"security":[{"ApiKeyAuth":[]}],"responses":{"200":{"description":"Workflow started successfully","content":{"application/json":{"schema":{"type":"object","properties":{"message":{"type":"string","example":"Workflow started"},"jobId":{"type":"string","description":"The ID of the created job"},"status":{"type":"string","description":"The status of the job","example":"running"}}}}}},"400":{"description":"Bad request (workflow not found, already running, etc.)","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"string"}}}}}},"401":{"description":"x-api-key missing or not authorized"},"409":{"description":"Workflow lifecycle conflict. Pass preview=true to rerun a stale preview instead.","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"string"},"reason":{"type":"string","enum":["WORKFLOW_NOT_FINALISED","PREVIEW_AWAITS_CUSTOMER_CONFIRMATION"]},"recoveryHint":{"type":"string"},"existingState":{"type":"string","enum":["DRAFT","PREVIEW"]}}}}}},"429":{"description":"Too many concurrent jobs","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"string"},"reason":{"type":"string","enum":["PIPELINE_CROWDED","USER_RATE_LIMIT"]}}}}}},"500":{"description":"Internal service error","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"string","example":"Internal service error. Please try again later."}}}}}}}}},"/v4/workflows/{workflowId}/schedule":{"put":{"summary":"Schedule a workflow","tags":["Workflows"],"parameters":[{"name":"workflowId","in":"path","required":true,"description":"The ID of the workflow to schedule","schema":{"type":"string"}}],"security":[{"ApiKeyAuth":[]}],"responses":{"200":{"description":"Workflow scheduled successfully","content":{"text/plain":{"schema":{"type":"string","example":"Workflow scheduled"}}}},"400":{"description":"Invalid date, workflowId missing, or workflow has no schedule"},"401":{"description":"x-api-key missing or not authorized"}},"requestBody":{"description":"ISO date (attention its timezone UTC) string required in request body","required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"date":{"type":"string","example":"2023-10-07T10:00:00.000Z"}}}}}}}},"/v4/workflows/{workflowId}/schema-validation-rules":{"get":{"summary":"Get data quality rules for a workflow","tags":["Data Quality"],"description":"Returns the per-field data quality rules persisted on the workflow.\nThe response is a map keyed by schema field name. A workflow without any rules returns `rules: null`.\n","parameters":[{"name":"workflowId","in":"path","required":true,"description":"ID of the workflow","schema":{"type":"string"}}],"security":[{"ApiKeyAuth":[]}],"responses":{"200":{"description":"Rules retrieved successfully","content":{"application/json":{"schema":{"type":"object","required":["rules"],"properties":{"rules":{"nullable":true,"allOf":[{"$ref":"#/components/schemas/WorkflowSchemaValidationRules"}]}}}}}},"400":{"description":"Invalid workflow ID format"},"401":{"description":"Unauthorized"},"404":{"description":"Workflow not found"},"500":{"description":"Internal server error"}}},"put":{"summary":"Upsert data quality rules for a workflow","tags":["Data Quality"],"description":"Patch-merge the per-field data quality rules persisted on the workflow. Fields included in the\nrequest body replace any existing rules for those fields; fields not included are left untouched.\nTo remove a field's rules, call the corresponding `DELETE` endpoint instead.\nRule edits take effect on the next workflow run.\n","parameters":[{"name":"workflowId","in":"path","required":true,"description":"ID of the workflow","schema":{"type":"string"}}],"security":[{"ApiKeyAuth":[]}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkflowSchemaValidationRules"}}}},"responses":{"200":{"description":"Rules updated successfully. Returns the merged ruleset.","content":{"application/json":{"schema":{"type":"object","required":["rules"],"properties":{"rules":{"$ref":"#/components/schemas/WorkflowSchemaValidationRules"}}}}}},"400":{"description":"Invalid workflow ID or invalid rule payload"},"401":{"description":"Unauthorized"},"404":{"description":"Workflow not found"},"500":{"description":"Internal server error"}}}},"/v4/workflows/{workflowId}/schema-validation-rules/{fieldName}":{"delete":{"summary":"Delete data quality rules for a single field","tags":["Data Quality"],"description":"Remove all data quality rules for a single schema field on a workflow.\nOther fields' rules are left untouched.\n","parameters":[{"name":"workflowId","in":"path","required":true,"description":"ID of the workflow","schema":{"type":"string"}},{"name":"fieldName","in":"path","required":true,"description":"Name of the schema field whose rules should be removed","schema":{"type":"string"}}],"security":[{"ApiKeyAuth":[]}],"responses":{"200":{"description":"Rules removed (or no-op if the field had no rules). Returns the remaining ruleset.","content":{"application/json":{"schema":{"type":"object","required":["rules"],"properties":{"rules":{"$ref":"#/components/schemas/WorkflowSchemaValidationRules"}}}}}},"400":{"description":"Invalid workflow ID format or missing fieldName"},"401":{"description":"Unauthorized"},"404":{"description":"Workflow not found"},"500":{"description":"Internal server error"}}}},"/v4/workflows/{workflowId}/sql":{"post":{"summary":"Generate a DuckDB query from a natural-language request","description":"Generates SQL without executing it. Requires read access to the workflow. Send the selected dataset's columns and up to five sample rows. Ambiguous requests use reasonable defaults explained in the response. A null SQL result explains why the request cannot be answered.","tags":["Workflows"],"security":[{"ApiKeyAuth":[]}],"parameters":[{"in":"path","name":"workflowId","required":true,"schema":{"type":"string"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["prompt","columns","sampleRows"],"properties":{"prompt":{"type":"string","minLength":1,"maxLength":2000},"columns":{"type":"array","minItems":1,"maxItems":200,"items":{"type":"object","required":["name","type"],"properties":{"name":{"type":"string","maxLength":256},"type":{"type":"string","maxLength":256}}}},"sampleRows":{"type":"array","maxItems":5,"items":{"type":"array","maxItems":200,"items":{"type":"string","maxLength":500}}}}}}}},"responses":{"200":{"description":"Generated SQL with assumptions, or an explanation of missing data or unsupported requests","content":{"application/json":{"schema":{"type":"object","required":["sql","explanation"],"properties":{"sql":{"type":"string","nullable":true},"explanation":{"type":"string"}}}}}},"400":{"description":"Invalid request"},"401":{"description":"Unauthorized"},"403":{"description":"Access denied"},"404":{"description":"Workflow not found"},"413":{"description":"Query context is too large"},"429":{"description":"Too many SQL requests for this team"},"502":{"description":"SQL generation failed"},"503":{"description":"SQL generation is not configured"}}}},"/v4/workflows/{workflowId}/stop":{"put":{"summary":"Stop a running workflow","description":"Cancels the active run for the specified workflow. Queued and pending steps are removed from the pipeline; the in-flight step may still complete.","tags":["Workflows"],"parameters":[{"name":"workflowId","in":"path","required":true,"description":"The ID of the workflow to stop","schema":{"type":"string"}}],"security":[{"ApiKeyAuth":[]}],"responses":{"200":{"description":"Workflow stop initiated","content":{"application/json":{"schema":{"type":"object","properties":{"message":{"type":"string","example":"Workflow run is being stopped"}}}}}},"400":{"description":"No running job found"},"401":{"description":"x-api-key missing or not authorized"},"404":{"description":"Workflow not found"},"409":{"description":"Workflow run cannot be stopped (e.g. during initial Shelly build)"}}}},"/v4/workflows/{workflowId}/triggers":{"get":{"summary":"List workflow triggers","description":"Get the triggers where the specified workflow is the source (`triggers`)\nand the triggers where it is the target (`incoming`). Outgoing rows are\nalways returned; each carries `targetWorkflowName` when the caller can\naccess the target. Incoming rows are returned only when the caller can\naccess the source workflow, and each carries `sourceWorkflowName`.\n`count` is the outgoing trigger count.\n","tags":["Workflow Triggers"],"parameters":[{"name":"workflowId","in":"path","required":true,"description":"ID of the source workflow","schema":{"type":"string"}},{"name":"x-api-key","in":"header","required":false,"schema":{"type":"string"}},{"name":"Authorization","in":"header","required":false,"schema":{"type":"string"}}],"security":[{"ApiKeyAuth":[]},{"BearerAuth":[]}],"responses":{"200":{"description":"Triggers retrieved successfully"},"400":{"description":"Invalid workflow ID"},"401":{"description":"Unauthorized"},"404":{"description":"Workflow not found"},"500":{"description":"Internal server error"}}},"post":{"summary":"Create a workflow trigger","description":"Create a trigger that fires when the source workflow emits an event.\nThe target must share the source ownership scope (same team for team\nworkflows, or the same user for personal workflows) and must not be a\nrealtime workflow. Superadmins are subject to the same scope check on\nthe public endpoint.\n","tags":["Workflow Triggers"],"parameters":[{"name":"workflowId","in":"path","required":true,"description":"ID of the source workflow","schema":{"type":"string"}},{"name":"x-api-key","in":"header","required":false,"schema":{"type":"string"}},{"name":"Authorization","in":"header","required":false,"schema":{"type":"string"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["targetWorkflowId","eventType"],"properties":{"targetWorkflowId":{"type":"string","description":"ID of the workflow to trigger"},"eventType":{"type":"string","enum":["workflow_started","workflow_finished","workflow_export_completed","workflow_failed","workflow_recovered","workflow_sample_finished","workflow_data_change","workflow_data_quality_change","workflow_health_degraded"],"description":"Event type that triggers the target workflow"},"enabled":{"type":"boolean","default":true,"description":"Whether the trigger is enabled"}}}}}},"security":[{"ApiKeyAuth":[]},{"BearerAuth":[]}],"responses":{"201":{"description":"Trigger created successfully"},"400":{"description":"Invalid input, target is a realtime workflow, or the workflow would trigger itself"},"401":{"description":"Unauthorized"},"403":{"description":"No access to target workflow, or target is outside the source ownership scope"},"404":{"description":"Workflow not found"},"409":{"description":"Duplicate trigger, or source/target ownership is moving teams"},"422":{"description":"Source workflow already has the maximum number of triggers (5)"},"500":{"description":"Internal server error"}}}},"/v4/workflows/{workflowId}/triggers/{triggerId}":{"get":{"summary":"Get a specific trigger","tags":["Workflow Triggers"],"parameters":[{"name":"workflowId","in":"path","required":true,"schema":{"type":"string"}},{"name":"triggerId","in":"path","required":true,"schema":{"type":"string"}},{"name":"x-api-key","in":"header","required":false,"schema":{"type":"string"}},{"name":"Authorization","in":"header","required":false,"schema":{"type":"string"}}],"security":[{"ApiKeyAuth":[]},{"BearerAuth":[]}],"responses":{"200":{"description":"Trigger retrieved successfully"},"400":{"description":"Invalid ID"},"401":{"description":"Unauthorized"},"404":{"description":"Trigger or workflow not found"},"500":{"description":"Internal server error"}}},"patch":{"summary":"Update a trigger","description":"Update trigger properties (eventType, enabled)","tags":["Workflow Triggers"],"parameters":[{"name":"workflowId","in":"path","required":true,"schema":{"type":"string"}},{"name":"triggerId","in":"path","required":true,"schema":{"type":"string"}},{"name":"x-api-key","in":"header","required":false,"schema":{"type":"string"}},{"name":"Authorization","in":"header","required":false,"schema":{"type":"string"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"eventType":{"type":"string","enum":["workflow_started","workflow_finished","workflow_export_completed","workflow_failed","workflow_recovered","workflow_sample_finished","workflow_data_change","workflow_data_quality_change","workflow_health_degraded"]},"enabled":{"type":"boolean"}}}}}},"security":[{"ApiKeyAuth":[]},{"BearerAuth":[]}],"responses":{"200":{"description":"Trigger updated successfully"},"400":{"description":"Invalid input"},"401":{"description":"Unauthorized"},"404":{"description":"Trigger or workflow not found"},"409":{"description":"Update would create a duplicate"},"500":{"description":"Internal server error"}}},"delete":{"summary":"Delete a trigger","tags":["Workflow Triggers"],"parameters":[{"name":"workflowId","in":"path","required":true,"schema":{"type":"string"}},{"name":"triggerId","in":"path","required":true,"schema":{"type":"string"}},{"name":"x-api-key","in":"header","required":false,"schema":{"type":"string"}},{"name":"Authorization","in":"header","required":false,"schema":{"type":"string"}}],"security":[{"ApiKeyAuth":[]},{"BearerAuth":[]}],"responses":{"200":{"description":"Trigger deleted successfully"},"400":{"description":"Invalid ID"},"401":{"description":"Unauthorized"},"404":{"description":"Trigger or workflow not found"},"500":{"description":"Internal server error"}}}},"/v5/agent":{"post":{"operationId":"v5AgentPrompt","summary":"Create or continue a public Agent session","description":"Creates a draft workflow-backed Assistant session. Explicit productType=realtime dispatches the Julie realtime lane after realtime notification settings are provisioned.","tags":["Agent"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AgentPromptRequest"}}}},"responses":{"202":{"description":"Agent prompt accepted","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AgentPromptResponse"}}}},"400":{"description":"Invalid request body or realtime notification settings"},"403":{"description":"Authenticated user cannot create workflows for the active team"},"404":{"description":"Template, Assistant session, or thread not found"},"409":{"description":"Agent prompt conflicts with the requested context"}}}},"/v5/agent/workflows/{workflowId}/timeline":{"get":{"operationId":"v5AgentWorkflowAssistantTimeline","summary":"Read customer-visible Assistant message history","description":"Returns user messages, Assistant messages, and clarification questions from the latest Lighthouse/Shelly or Julie customer thread. Internal and operations lanes are never selectable.","tags":["Agent"],"parameters":[{"name":"workflowId","in":"path","required":true,"schema":{"type":"string","format":"uuid"}},{"name":"cursor","in":"query","schema":{"type":"string"},"description":"Opaque nextCursor from a previous response, used to read older messages."},{"name":"limit","in":"query","schema":{"type":"integer","minimum":1,"maximum":100,"default":50}}],"responses":{"200":{"description":"Customer-visible Assistant message history","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AssistantHistoryResponse"}}}},"400":{"description":"Invalid workflow ID, limit, or cursor"},"403":{"description":"Authenticated principal cannot read workflows"},"404":{"description":"Workflow not found for the authenticated team"},"409":{"description":"Workflow has no Assistant session or customer-facing thread"},"502":{"description":"Assistant history storage is unavailable"}}}},"/v5/agent/workflows/{workflowId}/assistant/messages":{"post":{"operationId":"v5AgentWorkflowAssistantMessage","summary":"Request an Assistant update to an existing workflow","description":"Bootstraps or reuses the workflow's customer Assistant session and enqueues update instructions without changing the workflow ID.","tags":["Agent"],"parameters":[{"name":"workflowId","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkflowAssistantMessageRequest"}}}},"responses":{"202":{"description":"Workflow Assistant update accepted","content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkflowAssistantMessageResponse"}}}},"400":{"description":"Invalid workflow ID or request body"},"404":{"description":"Workflow or Assistant session not found"},"409":{"description":"Assistant session or thread conflict"}}}},"/v5/agent/{sessionId}/pause-state":{"get":{"operationId":"v5AgentPauseState","summary":"Get durable Assistant pause and question state","tags":["Agent"],"parameters":[{"name":"sessionId","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"responses":{"200":{"description":"Assistant pause state","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AssistantPauseStateResponse"}}}},"404":{"description":"Session not found"},"409":{"description":"Invalid session pause state"},"503":{"description":"Assistant manager temporarily unavailable"}}}},"/v5/agent/answer":{"post":{"operationId":"v5AgentAnswer","summary":"Answer a durable Assistant question","tags":["Agent"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AssistantAnswerRequest"}}}},"responses":{"200":{"description":"Answer accepted and session resume requested","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AssistantAnswerResponse"}}}},"400":{"description":"Invalid request body"},"404":{"description":"Session or question not found"},"409":{"description":"Question has already resumed or cannot accept an answer"}}}},"/v5/agent/{sessionId}/interrupt":{"post":{"operationId":"v5AgentInterrupt","summary":"Safely interrupt an active Assistant session","tags":["Agent"],"parameters":[{"name":"sessionId","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"responses":{"200":{"description":"Interrupt accepted or the session was already paused","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AssistantControlResponse"}}}},"404":{"description":"Session not found for the authenticated team"},"409":{"description":"Session cannot be interrupted from its current state"}}}},"/v5/agent/{sessionId}/resume":{"post":{"operationId":"v5AgentResume","summary":"Resume an inactive or interrupted Assistant session","description":"Resumes with the persona persisted on the session, preserving Lighthouse versus Julie behavior.","tags":["Agent"],"parameters":[{"name":"sessionId","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"responses":{"202":{"description":"Resume accepted","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AssistantResumeResponse"}}}},"404":{"description":"Session not found for the authenticated team"},"409":{"description":"Session is already active or cannot be resumed"}}}},"/v5/agent/{sessionId}/stop":{"post":{"operationId":"v5AgentStop","summary":"Stop an active Assistant session","tags":["Agent"],"parameters":[{"name":"sessionId","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"responses":{"200":{"description":"Stop accepted","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AssistantControlResponse"}}}},"404":{"description":"Session not found for the authenticated team"},"409":{"description":"Session is not active"}}}},"/v5/agent/data/{sessionId}/strategy":{"get":{"operationId":"v5AgentStrategy","summary":"Get the latest customer-safe Assistant extraction strategy","description":"Returns strategy null when the session exists but no build strategy is available yet.","tags":["Agent"],"parameters":[{"name":"sessionId","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"responses":{"200":{"description":"Latest extraction strategy, or null while unavailable","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AssistantStrategyResponse"}}}},"404":{"description":"Session not found"}}}},"/v5/agent/data/{sessionId}/builds":{"get":{"operationId":"v5AgentBuilds","summary":"List extraction script builds for an Assistant session","description":"Requires the ACCESS_SOURCE_CODE feature flag. Returns versions/statuses only, newest first, and only builds whose source currently passes Kadoa's source review; other builds are left out.","tags":["Agent"],"parameters":[{"name":"sessionId","in":"path","required":true,"schema":{"type":"string","format":"uuid"}},{"name":"limit","in":"query","schema":{"type":"integer","minimum":1,"maximum":100,"default":20}},{"name":"cursor","in":"query","schema":{"type":"string"}}],"responses":{"200":{"description":"Build history page","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AgentBuildsResponse"}}}},"403":{"description":"Feature flag not enabled for the account"},"404":{"description":"Session not found"}}}},"/v5/agent/data/{sessionId}/builds/{buildId}/input":{"get":{"operationId":"v5AgentBuildInput","summary":"Get the extraction script source of one build","description":"Requires the ACCESS_SOURCE_CODE feature flag. Returns the script source, no file names, for builds whose source currently passes Kadoa's source review.","tags":["Agent"],"parameters":[{"name":"sessionId","in":"path","required":true,"schema":{"type":"string","format":"uuid"}},{"name":"buildId","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"responses":{"200":{"description":"Build script source","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AgentBuildInputResponse"}}}},"403":{"description":"Feature flag not enabled for the account"},"404":{"description":"Build not found for this session/team, or its source is not available (BUILD_SOURCE_NOT_VIEWABLE)"}}}},"/v5/agent/{sessionId}":{"delete":{"operationId":"v5AgentDeleteSession","summary":"Delete an inactive Assistant session","description":"Deletes the session and its related data. Only inactive sessions with a customer-facing thread can be deleted. Re-sending after a successful delete returns 404, which callers should treat as already done.","tags":["Agent"],"parameters":[{"name":"sessionId","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"responses":{"204":{"description":"Session deleted"},"400":{"description":"sessionId is not a UUID","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AgentErrorEnvelope"}}}},"404":{"description":"Session not found for the authenticated team"},"409":{"description":"Session is active, or has no customer-facing thread"}}}},"/v5/agent/workflows/{workflowId}/assistant-session":{"post":{"operationId":"v5AgentWorkflowAssistantSession","summary":"Start (or return) the workflow's Assistant session","description":"Bootstraps the customer-facing Assistant lane for a workflow. Concurrent bootstraps converge on the same session; 201 marks a fresh start, 200 an already-existing lane.","tags":["Agent"],"parameters":[{"name":"workflowId","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"responses":{"200":{"description":"Assistant already started"},"201":{"description":"Assistant started"},"400":{"description":"Workflow is not eligible for the Assistant","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AgentErrorEnvelope"}}}},"404":{"description":"Workflow not found for the authenticated team"},"502":{"description":"Bootstrap outcome unknown (ASSISTANT_BOOTSTRAP_OUTCOME_UNKNOWN) — re-send safely","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AgentErrorEnvelope"}}}}}}},"/v5/changes":{"get":{"summary":"Get all data changes (PostgreSQL)","tags":["Workflows"],"parameters":[{"name":"x-api-key","in":"header","required":false,"description":"API key for authorization","schema":{"type":"string"}},{"name":"Authorization","in":"header","required":false,"description":"Bearer token for authorization","schema":{"type":"string"}},{"name":"workflowIds","in":"query","required":false,"description":"Comma-separated list of workflow IDs. If not provided, returns changes for all ACTIVE workflows","schema":{"type":"string"}},{"name":"startDate","in":"query","required":false,"description":"Start date to filter changes (ISO format)","schema":{"type":"string","format":"date-time"}},{"name":"endDate","in":"query","required":false,"description":"End date to filter changes (ISO format)","schema":{"type":"string","format":"date-time"}},{"name":"skip","in":"query","required":false,"description":"Number of records to skip for pagination","schema":{"type":"integer"}},{"name":"limit","in":"query","required":false,"description":"Number of records to return for pagination","schema":{"type":"integer"}}],"security":[{"ApiKeyAuth":[]},{"BearerAuth":[]}],"responses":{"200":{"description":"Workflow changes returned successfully","content":{"application/json":{"schema":{"type":"object","properties":{"timestamp":{"type":"string","format":"date-time","description":"Timestamp of the response"},"changesCount":{"type":"integer","description":"Total number of changes found"},"changes":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string","description":"Unique identifier of the change"},"workflowId":{"type":"string","description":"ID of the workflow this change belongs to"},"data":{"type":"array","nullable":true,"description":"Current state of the data after the change","items":{"type":"object"}},"dataPending":{"type":"boolean","description":"True when durable change data is still being stored; change events are emitted first so users see changes as fast as possible."},"differences":{"type":"array","description":"Structured representation of changes with object-based diffing. List responses omit visualDiff metadata.","items":{"type":"object","properties":{"type":{"type":"string","description":"Type of change (added, removed, or changed)","enum":["added","removed","changed"]},"fields":{"type":"array","description":"List of field changes","items":{"type":"object","properties":{"key":{"type":"string","description":"Field name"},"value":{"type":"string","description":"Current field value"},"previousValue":{"type":"string","description":"Previous field value (only present for changed type)"}}}}}}},"url":{"type":"string","description":"URL where the change was detected"},"summary":{"type":"string","nullable":true,"description":"AI-generated one-sentence summary of the data change. Null if generation failed, feature is disabled, or change predates the feature."},"screenshotUrl":{"type":"string","description":"URL of the screenshot taken when the change was detected"},"createdAt":{"type":"string","format":"date-time","description":"Timestamp when the change was created"}}}},"pagination":{"type":"object","properties":{"totalCount":{"type":"integer","description":"Total number of changes found"},"page":{"type":"integer","description":"Current page number"},"totalPages":{"type":"integer","description":"Total number of pages"},"limit":{"type":"integer","description":"Number of records per page"}}}}}}}},"400":{"description":"Bad request (invalid date range or workflow IDs)"},"401":{"description":"Unauthorized (invalid or missing API key or Bearer token)"},"500":{"description":"Internal server error"}},"x-code-samples":[{"lang":"curl","source":"curl -X GET \"https://api.kadoa.com/v5/workflows/changes?workflowIds=123,456&startDate=2024-01-01T00:00:00Z&endDate=2024-03-01T00:00:00Z\" \\\n-H \"x-api-key: YOUR_API_KEY\"\n"},{"lang":"python","source":"import requests\n\nurl = \"https://api.kadoa.com/v5/workflows/changes\"\nheaders = {\n    \"x-api-key\": \"YOUR_API_KEY\"\n}\nparams = {\n    \"workflowIds\": \"123,456\",\n    \"startDate\": \"2024-01-01T00:00:00Z\",\n    \"endDate\": \"2024-03-01T00:00:00Z\"\n}\n\nresponse = requests.get(url, headers=headers, params=params)\ndata = response.json()\nprint(data)\n"}]}},"/v5/changes/{changeId}":{"get":{"summary":"Get data change by ID (PostgreSQL)","tags":["Workflows"],"parameters":[{"name":"x-api-key","in":"header","required":false,"description":"API key for authorization","schema":{"type":"string"}},{"name":"Authorization","in":"header","required":false,"description":"Bearer token for authorization","schema":{"type":"string"}},{"name":"changeId","in":"path","required":true,"description":"ID of the workflow change to retrieve","schema":{"type":"string"}}],"security":[{"ApiKeyAuth":[]},{"BearerAuth":[]}],"responses":{"200":{"description":"Workflow change returned successfully","content":{"application/json":{"schema":{"type":"object","properties":{"id":{"type":"string","description":"Unique identifier of the change"},"workflowId":{"type":"string","description":"ID of the workflow this change belongs to"},"data":{"type":"array","nullable":true,"description":"Current state of the data after the change","items":{"type":"object"}},"dataPending":{"type":"boolean","description":"True when durable change data is still being stored; change events are emitted first so users see changes as fast as possible."},"differences":{"type":"array","description":"Structured representation of changes with object-based diffing","items":{"type":"object","properties":{"type":{"type":"string","description":"Type of change (added, removed, or changed)","enum":["added","removed","changed"]},"fields":{"type":"array","description":"List of field changes","items":{"type":"object","properties":{"key":{"type":"string","description":"Field name"},"value":{"type":"string","description":"Current field value"},"previousValue":{"type":"string","description":"Previous field value (only present for changed type)"}}}},"visualDiff":{"type":"object","nullable":true,"description":"Screenshot-space boxes for this diff item. Present only when row grounding is available.","properties":{"current":{"type":"object","description":"Boxes on the current change screenshot for added or changed rows.","properties":{"url":{"type":"string"},"width":{"type":"number"},"height":{"type":"number"},"rowBox":{"type":"object","properties":{"x":{"type":"number"},"y":{"type":"number"},"width":{"type":"number"},"height":{"type":"number"}}},"fieldBoxes":{"type":"object","additionalProperties":{"type":"object","properties":{"x":{"type":"number"},"y":{"type":"number"},"width":{"type":"number"},"height":{"type":"number"}}}}}},"previous":{"type":"object","description":"Boxes on the previous workflow job screenshot for removed or changed rows.","properties":{"url":{"type":"string"},"width":{"type":"number"},"height":{"type":"number"},"rowBox":{"type":"object","properties":{"x":{"type":"number"},"y":{"type":"number"},"width":{"type":"number"},"height":{"type":"number"}}},"fieldBoxes":{"type":"object","additionalProperties":{"type":"object","properties":{"x":{"type":"number"},"y":{"type":"number"},"width":{"type":"number"},"height":{"type":"number"}}}}}}}}}}},"url":{"type":"string","description":"URL where the change was detected"},"summary":{"type":"string","nullable":true,"description":"AI-generated one-sentence summary of the data change. Null if generation failed, feature is disabled, or change predates the feature."},"screenshotUrl":{"type":"string","description":"URL of the screenshot taken when the change was detected"},"previousJobScreenshotUrl":{"type":"string","nullable":true,"description":"Screenshot URL from the previous workflow job used by visualDiff.previous boxes."},"createdAt":{"type":"string","format":"date-time","description":"Timestamp when the change was created"}}}}}},"400":{"description":"Bad request (invalid change ID format)"},"401":{"description":"Unauthorized (invalid or missing API key or Bearer token)"},"404":{"description":"Change not found or no access to the corresponding workflow"},"500":{"description":"Internal server error"}},"x-code-samples":[{"lang":"curl","source":"curl -X GET \"https://api.kadoa.com/v5/changes/123456789\" \\\n-H \"x-api-key: YOUR_API_KEY\"\n"},{"lang":"python","source":"import requests\n\nurl = \"https://api.kadoa.com/v5/changes/123456789\"\nheaders = {\n    \"x-api-key\": \"YOUR_API_KEY\"\n}\n\nresponse = requests.get(url, headers=headers)\ndata = response.json()\nprint(data)\n"}]}},"/v5/notifications/workflows/{workflowId}/changes/{changeId}/csv":{"get":{"summary":"Download the changed-records CSV for a data change","description":"Accepts either normal team authentication or a signed link minted for a notification. Pass `latest` as changeId to get the workflow's most recent change, which the settings editor uses as a sample download.\n","tags":["Notifications"],"parameters":[{"in":"path","name":"workflowId","required":true,"schema":{"type":"string"}},{"in":"path","name":"changeId","required":true,"schema":{"type":"string"},"description":"Change id, or `latest` for the most recent change."},{"in":"query","name":"expires","schema":{"type":"string"}},{"in":"query","name":"sig","schema":{"type":"string"}}],"responses":{"200":{"description":"CSV file","content":{"text/csv":{"schema":{"type":"string"}}}},"404":{"description":"Change not found"},"409":{"description":"The change set is no longer retrievable"}}}},"/v5/notifications/channels":{"get":{"summary":"Retrieve all notification channels","tags":["Notifications"],"security":[{"ApiKeyAuth":[]}],"parameters":[{"in":"query","name":"workflowId","schema":{"type":"string"},"description":"Workflow ID (optional, if provided returns channels linked to this workflow)"},{"in":"query","name":"includeConfigurations","schema":{"type":"boolean","default":true},"description":"Include linked notification configurations with workflow information"}],"responses":{"200":{"description":"Channels retrieved successfully","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"channels":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string"},"name":{"type":"string"},"channelType":{"type":"string"},"config":{"type":"object","description":"Configuration object specific to the channel type","oneOf":[{"$ref":"#/components/schemas/EmailChannelConfig"},{"$ref":"#/components/schemas/SlackChannelConfig"},{"$ref":"#/components/schemas/WebhookChannelConfig"},{"$ref":"#/components/schemas/WebsocketChannelConfig"}]},"linkedConfigurations":{"type":"array","description":"List of notification configurations linked to this channel","items":{"type":"object","properties":{"configurationId":{"type":"string","description":"The configuration ID"},"workflowId":{"type":"string","nullable":true,"description":"Workflow ID if this is a workflow-specific configuration, null for workspace-level configurations"},"eventType":{"type":"string","description":"Event type for this configuration (e.g., workflow_sample_finished, workflow_data_change)"},"enabled":{"type":"boolean","description":"Whether this configuration is enabled"}}}},"createdAt":{"type":"string"},"updatedAt":{"type":"string"}}}}}},"status":{"type":"string"},"message":{"type":"string"}}}}}},"401":{"description":"Unauthorized"},"500":{"description":"Internal server error"}}},"post":{"summary":"Create a new notification channel","tags":["Notifications"],"security":[{"ApiKeyAuth":[]}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["name","channelType","config"],"properties":{"name":{"type":"string"},"channelType":{"type":"string","enum":["EMAIL","SLACK","WEBHOOK","WEBSOCKET"]},"config":{"type":"object","description":"Configuration object specific to the channel type","oneOf":[{"$ref":"#/components/schemas/EmailChannelConfig"},{"$ref":"#/components/schemas/SlackChannelConfig"},{"$ref":"#/components/schemas/WebhookChannelConfig"},{"$ref":"#/components/schemas/WebsocketChannelConfig"}]}}}}}},"responses":{"201":{"description":"Channel created successfully","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"channel":{"type":"object"}}},"status":{"type":"string"},"message":{"type":"string"}}}}}},"400":{"description":"Bad request"},"401":{"description":"Unauthorized"},"500":{"description":"Internal server error"}}}},"/v5/notifications/channels/{channelId}":{"get":{"summary":"Retrieve a specific notification channel","tags":["Notifications"],"security":[{"ApiKeyAuth":[]}],"parameters":[{"in":"path","name":"channelId","required":true,"schema":{"type":"string"},"description":"Channel ID"},{"in":"query","name":"includeConfigurations","schema":{"type":"boolean","default":true},"description":"Include linked notification configurations with workflow information"}],"responses":{"200":{"description":"Channel retrieved successfully","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"channel":{"type":"object","properties":{"id":{"type":"string"},"name":{"type":"string"},"channelType":{"type":"string"},"config":{"type":"object","description":"Configuration object specific to the channel type","oneOf":[{"$ref":"#/components/schemas/EmailChannelConfig"},{"$ref":"#/components/schemas/SlackChannelConfig"},{"$ref":"#/components/schemas/WebhookChannelConfig"},{"$ref":"#/components/schemas/WebsocketChannelConfig"}]},"linkedConfigurations":{"type":"array","description":"List of notification configurations linked to this channel","items":{"type":"object","properties":{"configurationId":{"type":"string","description":"The configuration ID"},"workflowId":{"type":"string","nullable":true,"description":"Workflow ID if this is a workflow-specific configuration, null for workspace-level configurations"},"eventType":{"type":"string","description":"Event type for this configuration (e.g., workflow_sample_finished, workflow_data_change)"},"enabled":{"type":"boolean","description":"Whether this configuration is enabled"}}}},"createdAt":{"type":"string"},"updatedAt":{"type":"string"}}}}},"status":{"type":"string"},"message":{"type":"string"}}}}}},"401":{"description":"Unauthorized"},"404":{"description":"Channel not found"},"500":{"description":"Internal server error"}}},"put":{"summary":"Update a notification channel","tags":["Notifications"],"security":[{"ApiKeyAuth":[]}],"parameters":[{"in":"path","name":"channelId","required":true,"schema":{"type":"string"},"description":"Channel ID"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["name","channelType","config"],"properties":{"name":{"type":"string"},"channelType":{"type":"string","enum":["EMAIL","SLACK","WEBHOOK","WEBSOCKET"]},"config":{"type":"object","description":"Configuration object specific to the channel type","oneOf":[{"$ref":"#/components/schemas/EmailChannelConfig"},{"$ref":"#/components/schemas/SlackChannelConfig"},{"$ref":"#/components/schemas/WebhookChannelConfig"},{"$ref":"#/components/schemas/WebsocketChannelConfig"}]}}}}}},"responses":{"200":{"description":"Channel updated successfully","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"channel":{"type":"object"}}},"status":{"type":"string"},"message":{"type":"string"}}}}}},"400":{"description":"Bad request"},"401":{"description":"Unauthorized"},"404":{"description":"Channel not found"},"500":{"description":"Internal server error"}}},"delete":{"summary":"Delete a notification channel","tags":["Notifications"],"security":[{"ApiKeyAuth":[]}],"parameters":[{"in":"path","name":"channelId","required":true,"schema":{"type":"string"},"description":"Channel ID"}],"responses":{"200":{"description":"Channel deleted successfully","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"channelId":{"type":"string"}}},"status":{"type":"string"},"message":{"type":"string"}}}}}},"401":{"description":"Unauthorized"},"404":{"description":"Channel not found"},"500":{"description":"Internal server error"}}}},"/v5/notifications/event-types":{"get":{"summary":"Retrieve all available notification event types","tags":["Notifications"],"security":[{"ApiKeyAuth":[]}],"responses":{"200":{"description":"Event types retrieved successfully","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"eventTypes":{"type":"array","items":{"type":"object","properties":{"type":{"type":"string"},"category":{"type":"string"},"description":{"type":"string"},"version":{"type":"string"},"schema":{"type":"object"}}}}}},"status":{"type":"string"},"message":{"type":"string"}}}}}},"401":{"description":"Unauthorized"},"500":{"description":"Internal server error"}}}},"/v5/notifications/event-types/{eventType}":{"get":{"summary":"Retrieve a specific event type details","tags":["Notifications"],"security":[{"ApiKeyAuth":[]}],"parameters":[{"in":"path","name":"eventType","required":true,"schema":{"type":"string"},"description":"Event type identifier"}],"responses":{"200":{"description":"Event type details retrieved successfully","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"eventType":{"type":"object","properties":{"type":{"type":"string"},"category":{"type":"string"},"description":{"type":"string"},"version":{"type":"string"},"schema":{"type":"object"}}}}},"status":{"type":"string"},"message":{"type":"string"}}}}}},"401":{"description":"Unauthorized"},"404":{"description":"Event type not found"},"500":{"description":"Internal server error"}}}},"/v5/notifications/workflows/{workflowId}/jobs/{jobId}/csv":{"get":{"summary":"Download the extracted records of a workflow run as CSV","description":"Accepts either normal team authentication or a signed link minted for a workflow-finished notification.\n","tags":["Notifications"],"parameters":[{"in":"path","name":"workflowId","required":true,"schema":{"type":"string"}},{"in":"path","name":"jobId","required":true,"schema":{"type":"string"}},{"in":"query","name":"expires","schema":{"type":"string"}},{"in":"query","name":"sig","schema":{"type":"string"}}],"responses":{"200":{"description":"CSV file","content":{"text/csv":{"schema":{"type":"string"}}}},"404":{"description":"Run not found"},"409":{"description":"The run holds no readable data, or its producing schema is unavailable"}}}},"/v5/notifications/logs":{"get":{"summary":"Retrieve notification event logs","tags":["Notifications"],"security":[{"ApiKeyAuth":[]}],"parameters":[{"in":"query","name":"workflowId","schema":{"type":"string"},"description":"Filter by workflow ID (optional)"},{"in":"query","name":"eventType","schema":{"type":"string"},"description":"Filter by event type (optional)"},{"in":"query","name":"startDate","schema":{"type":"string","format":"date-time"},"description":"Filter events from this date (optional)"},{"in":"query","name":"endDate","schema":{"type":"string","format":"date-time"},"description":"Filter events until this date (optional)"},{"in":"query","name":"limit","schema":{"type":"integer","default":50,"minimum":1,"maximum":100},"description":"Number of events to return (default 50, max 100)"},{"in":"query","name":"offset","schema":{"type":"integer","default":0,"minimum":0},"description":"Number of events to skip for pagination"}],"responses":{"200":{"description":"Event logs retrieved successfully","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"events":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string"},"workflowId":{"type":"string"},"eventType":{"type":"string"},"eventStatus":{"type":"string"},"channelConfig":{"type":"object"},"payload":{"type":"object"},"eventId":{"type":"string"},"createdAt":{"type":"string"}}}},"pagination":{"type":"object","properties":{"total":{"type":"integer"},"limit":{"type":"integer"},"offset":{"type":"integer"},"hasMore":{"type":"boolean"}}}}},"status":{"type":"string"},"message":{"type":"string"}}}}}},"401":{"description":"Unauthorized"},"500":{"description":"Internal server error"}}}},"/v5/notifications/test":{"post":{"summary":"Test a notification settings with mock data","tags":["Notifications"],"security":[{"ApiKeyAuth":[]}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["eventType"],"properties":{"eventType":{"type":"string","description":"Event type to test (e.g., workflow_finished, workflow_data_change)","example":"workflow_finished"},"workflowId":{"type":"string","description":"Optional workflow ID for workflow-specific testing","example":"workflow-123"}}}}}},"responses":{"200":{"description":"Test event sent successfully","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"eventId":{"type":"string","description":"Unique identifier for the event"},"eventType":{"type":"string","description":"Event type that was sent"},"workflowId":{"type":"string","description":"Workflow ID used in the event (if provided)"}}},"status":{"type":"string"},"message":{"type":"string"}}}}}},"400":{"description":"Invalid request (missing eventType or invalid eventType)"},"401":{"description":"Unauthorized"},"500":{"description":"Internal server error"}}}},"/v5/notifications/settings":{"get":{"summary":"Retrieve all notification settings","tags":["Notifications"],"security":[{"ApiKeyAuth":[]}],"parameters":[{"in":"query","name":"workflowId","schema":{"type":"string"},"description":"Workflow ID(s) - can be single ID, comma-separated IDs, or 'null' for workspace-level settings"},{"in":"query","name":"eventType","schema":{"type":"string","enum":["workflow_started","workflow_finished","workflow_failed","workflow_sample_finished","workflow_data_change","system_maintenance","service_degradation","credits_low","free_trial_ending"]},"description":"Event type filter (optional)"}],"responses":{"200":{"description":"Settings retrieved successfully","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"settings":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string"},"workflowId":{"type":"string"},"eventType":{"type":"string"},"eventConfiguration":{"type":"object"},"enabled":{"type":"boolean"},"channels":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string"},"name":{"type":"string"},"channelType":{"type":"string"}}}},"createdAt":{"type":"string"},"updatedAt":{"type":"string"}}}}}},"status":{"type":"string"},"message":{"type":"string"}}}}}},"401":{"description":"Unauthorized"},"500":{"description":"Internal server error"}}},"post":{"summary":"Create a new notification settings","tags":["Notifications"],"security":[{"ApiKeyAuth":[]}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["eventType","eventConfiguration"],"properties":{"workflowId":{"type":"string","description":"Workflow ID (optional, if not provided creates workspace-level settings)"},"eventType":{"type":"string","enum":["workflow_started","workflow_finished","workflow_failed","workflow_sample_finished","workflow_data_change","system_maintenance","service_degradation","credits_low","free_trial_ending"]},"eventConfiguration":{"type":"object","description":"Settings specific to the event type. Currently accepts an empty object {}. This object will be extended in future releases to support event-specific configuration options."},"enabled":{"type":"boolean","default":true},"channelIds":{"type":"array","items":{"type":"string"},"description":"Array of channel IDs to link to this Settings"}}}}}},"responses":{"201":{"description":"Settings created successfully","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"settings":{"type":"object","properties":{"id":{"type":"string"},"workflowId":{"type":"string"},"eventType":{"type":"string"},"eventConfiguration":{"type":"object"},"enabled":{"type":"boolean"},"channels":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string"},"name":{"type":"string"},"channelType":{"type":"string"}}}},"createdAt":{"type":"string"},"updatedAt":{"type":"string"}}}}},"status":{"type":"string"},"message":{"type":"string"}}}}}},"400":{"description":"Bad request (validation errors or duplicate settings)"},"401":{"description":"Unauthorized"},"500":{"description":"Internal server error"}}}},"/v5/notifications/settings/{settingsId}":{"get":{"summary":"Retrieve a specific notification settings","tags":["Notifications"],"security":[{"ApiKeyAuth":[]}],"parameters":[{"in":"path","name":"settingsId","required":true,"schema":{"type":"string"},"description":"Settings ID"}],"responses":{"200":{"description":"Settings retrieved successfully","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"settings":{"type":"object","properties":{"id":{"type":"string"},"workflowId":{"type":"string"},"eventType":{"type":"string"},"eventConfiguration":{"type":"object"},"enabled":{"type":"boolean"},"channels":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string"},"name":{"type":"string"},"channelType":{"type":"string"}}}},"createdAt":{"type":"string"},"updatedAt":{"type":"string"}}}}},"status":{"type":"string"},"message":{"type":"string"}}}}}},"401":{"description":"Unauthorized"},"404":{"description":"Settings not found"},"500":{"description":"Internal server error"}}},"put":{"summary":"Update a notification settings","tags":["Notifications"],"security":[{"ApiKeyAuth":[]}],"parameters":[{"in":"path","name":"settingsId","required":true,"schema":{"type":"string"},"description":"Settings ID"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"eventType":{"type":"string","enum":["workflow_started","workflow_finished","workflow_failed","workflow_sample_finished","workflow_data_change","system_maintenance","service_degradation","credits_low","free_trial_ending"]},"eventConfiguration":{"type":"object","description":"Settings specific to the event type. Currently accepts an empty object {}. This object will be extended in future releases to support event-specific configuration options."},"enabled":{"type":"boolean"},"channelIds":{"type":"array","items":{"type":"string"},"description":"Array of channel IDs to link to this settings"}}}}}},"responses":{"200":{"description":"Settings updated successfully","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"settings":{"type":"object","properties":{"id":{"type":"string"},"workflowId":{"type":"string"},"eventType":{"type":"string"},"eventConfiguration":{"type":"object"},"enabled":{"type":"boolean"},"channels":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string"},"name":{"type":"string"},"channelType":{"type":"string"}}}},"createdAt":{"type":"string"},"updatedAt":{"type":"string"}}}}},"status":{"type":"string"},"message":{"type":"string"}}}}}},"400":{"description":"Bad request (validation errors or duplicate settings)"},"401":{"description":"Unauthorized"},"404":{"description":"Settings not found"},"500":{"description":"Internal server error"}}},"delete":{"summary":"Delete a notification settings","tags":["Notifications"],"security":[{"ApiKeyAuth":[]}],"parameters":[{"in":"path","name":"settingsId","required":true,"schema":{"type":"string"},"description":"Settings ID"}],"responses":{"200":{"description":"Settings deleted successfully","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"settingsId":{"type":"string"}}},"status":{"type":"string"},"message":{"type":"string"}}}}}},"401":{"description":"Unauthorized"},"404":{"description":"Settings not found"},"500":{"description":"Internal server error"}}}},"/v5/workflows/{workflowId}/auditlog":{"get":{"summary":"Get workflow audit log entries","tags":["Workflows"],"parameters":[{"name":"x-api-key","in":"header","required":false,"description":"API key for authorization","schema":{"type":"string"}},{"name":"Authorization","in":"header","required":false,"description":"Bearer token for authorization","schema":{"type":"string"}},{"name":"workflowId","in":"path","required":true,"description":"ID of the workflow to retrieve audit logs from","schema":{"type":"string"}},{"name":"page","in":"query","required":false,"description":"Page number for pagination","schema":{"type":"integer","minimum":1,"default":1}},{"name":"limit","in":"query","required":false,"description":"Number of items per page","schema":{"type":"integer","minimum":1,"default":25}}],"security":[{"ApiKeyAuth":[]},{"BearerAuth":[]}],"responses":{"200":{"description":"Workflow audit log entries returned successfully","content":{"application/json":{"schema":{"type":"object","required":["id","timestamp","logEntriesCount","logEntries","pagination"],"properties":{"id":{"type":"string","description":"Workflow ID"},"timestamp":{"type":"string","format":"date-time","description":"Timestamp of the response"},"logEntriesCount":{"type":"integer","description":"Total number of log entries"},"logEntries":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string","description":"Audit log entry ID"},"operationType":{"type":"string","enum":["CREATE","UPDATE","DELETE"],"description":"Type of operation performed"},"userId":{"type":"string","description":"ID of the user who performed the operation"},"userEmail":{"type":"string","description":"Email of the user who performed the operation"},"previousValue":{"type":"object","description":"Previous state of the workflow"},"newValue":{"type":"object","description":"New state of the workflow"},"createdAt":{"type":"string","format":"date-time","description":"Timestamp when the operation was performed"},"requestSource":{"type":"string","nullable":true,"enum":["UI","API","SDK","MCP","CLI","ASSISTANT","SYSTEM"],"description":"Channel that originated the change"},"authMethod":{"type":"string","nullable":true,"description":"Authentication method used (e.g. JWT_TOKEN, PERSONAL_API_KEY, TEAM_API_KEY, SYSTEM)"}}}},"pagination":{"type":"object","properties":{"page":{"type":"integer","description":"Current page number"},"limit":{"type":"integer","description":"Number of items per page"},"totalPages":{"type":"integer","description":"Total number of pages"},"totalCount":{"type":"integer","description":"Total number of log entries"}}}}}}}},"400":{"description":"Bad request (invalid parameters)"},"401":{"description":"Unauthorized (invalid or missing API key or Bearer token)"},"404":{"description":"Workflow not found"},"500":{"description":"Internal server error"}}}},"/v5/workspaces/{workspaceId}/activity-usage":{"get":{"summary":"Get daily workflow totals, approvals, and extracted rows","description":"Returns informational usage across all execution modes. This data does not determine the workspace billing model.","tags":["Workspaces"],"parameters":[{"name":"workspaceId","in":"path","required":true,"schema":{"type":"string","format":"uuid"}},{"name":"days","in":"query","required":false,"description":"Number of trailing UTC days to return (1-366, default 30)","schema":{"type":"integer","default":30}},{"name":"x-api-key","in":"header","required":false,"schema":{"type":"string"}},{"name":"Authorization","in":"header","required":false,"schema":{"type":"string"}}],"security":[{"ApiKeyAuth":[]},{"BearerAuth":[]}],"responses":{"200":{"description":"Activity usage retrieved successfully","content":{"application/json":{"schema":{"type":"object","required":["start","end","totals","days"],"properties":{"start":{"type":"string","format":"date-time"},"end":{"type":"string","format":"date-time"},"totals":{"type":"object","required":["approvedWorkflows","extractedRows"],"properties":{"approvedWorkflows":{"type":"integer"},"extractedRows":{"type":"integer"}}},"days":{"type":"array","items":{"type":"object","required":["date","totalWorkflows","approvedWorkflows","extractedRows"],"properties":{"date":{"type":"string","format":"date"},"totalWorkflows":{"type":"integer"},"approvedWorkflows":{"type":"integer"},"extractedRows":{"type":"integer"}}}}}}}}},"400":{"description":"Invalid range"},"401":{"description":"Unauthorized"},"403":{"description":"Forbidden"},"404":{"description":"Workspace not found"},"500":{"description":"Internal server error"}}}},"/v5/workspaces/{workspaceId}/billable-workflows":{"get":{"summary":"List the billable workflows behind the current billing period (teams and organizations)","description":"The per-workflow detail behind the approved-workflows count. A workflow is billable if it has at least one successful (FINISHED), non-preview run whose finished_at falls inside the current billing period — of any current state, deleted included (deleted workflows still bill if they ran). Sourced from workflow jobs (immutable run facts), so the result is drift-free and reproducible.\n","tags":["Workspaces"],"parameters":[{"name":"workspaceId","in":"path","required":true,"description":"Workspace ID (team or organization)","schema":{"type":"string","format":"uuid"}},{"name":"x-api-key","in":"header","required":false,"schema":{"type":"string"}},{"name":"Authorization","in":"header","required":false,"schema":{"type":"string"}}],"security":[{"ApiKeyAuth":[]},{"BearerAuth":[]}],"responses":{"200":{"description":"Billable workflows retrieved successfully","content":{"application/json":{"schema":{"type":"object","properties":{"billingPeriod":{"type":"object","nullable":true,"description":"Null for a renewal-anchored workspace with no renewal_date (trial); the workflows list is then empty.","properties":{"start":{"type":"string","format":"date-time"},"end":{"type":"string","format":"date-time"}}},"count":{"type":"integer","description":"Number of billable workflows in the period"},"scheduledWorkflows":{"type":"integer","description":"ACTIVE workflows with an enabled schedule or a real-time runtime"},"activeCount":{"type":"integer","description":"Number of workflows in the Active billing model right now"},"activeSlotUsage":{"type":"number","format":"float","description":"Weighted slot usage for activeWorkflows"},"slotUsage":{"type":"number","format":"float","description":"Weighted slot usage for workflows in the current billing period"},"activeWorkflows":{"type":"array","description":"Workflow detail behind activeCount, using the enabled scheduled-or-realtime rule","items":{"type":"object","properties":{"workflowId":{"type":"string","format":"uuid"},"name":{"type":"string","nullable":true},"state":{"type":"string"},"scheduled":{"type":"boolean","description":"Enabled scheduled or real-time workflow"},"firstRunAt":{"type":"string","format":"date-time","nullable":true,"description":"First successful non-preview run in the trailing 30-day detail window"},"activeUntil":{"type":"string","format":"date-time","nullable":true,"description":"Retained for compatibility; always null because Active membership no longer expires from run history"},"billingMultiplier":{"type":"number","format":"float","description":"Slot usage assigned by Kadoa (0.1 Simple, 1 Standard, 2-10 Complex)"},"runsInPeriod":{"type":"integer","description":"Successful non-preview runs in the trailing 30-day detail window"},"totalRows":{"type":"integer"}}}},"workflows":{"type":"array","items":{"type":"object","properties":{"workflowId":{"type":"string","format":"uuid"},"name":{"type":"string","nullable":true},"state":{"type":"string","description":"Current workflow state (includes DELETED)"},"scheduled":{"type":"boolean","description":"ACTIVE and either on an active schedule or a live real-time monitor (recurring); else completed/one-off"},"firstRunAt":{"type":"string","format":"date-time"},"billingMultiplier":{"type":"number","format":"float","description":"Slot usage assigned by Kadoa (0.1 Simple, 1 Standard, 2-10 Complex)"},"runsInPeriod":{"type":"integer"},"totalRows":{"type":"integer","description":"Total rows extracted across the in-period runs"}}}}}}}}},"400":{"description":"Bad request"},"401":{"description":"Unauthorized"},"403":{"description":"Forbidden - insufficient permissions"},"404":{"description":"Workspace not found"},"500":{"description":"Internal server error"}}}},"/v5/workspaces/{workspaceId}/details":{"get":{"summary":"Get workspace details (supports teams and organizations)","tags":["Workspaces"],"parameters":[{"name":"workspaceId","in":"path","required":true,"description":"Workspace ID (team or organization)","schema":{"type":"string","format":"uuid"}},{"name":"x-api-key","in":"header","required":false,"description":"API key for authorization","schema":{"type":"string"}},{"name":"Authorization","in":"header","required":false,"description":"Bearer token for authorization","schema":{"type":"string"}}],"security":[{"ApiKeyAuth":[]},{"BearerAuth":[]}],"responses":{"200":{"description":"Workspace details retrieved successfully","content":{"application/json":{"schema":{"type":"object","properties":{"workspace":{"type":"object","properties":{"id":{"type":"string","format":"uuid","description":"Workspace ID"},"type":{"type":"string","enum":["team","organization"],"description":"Workspace type"},"name":{"type":"string","description":"Workspace name"},"description":{"type":"string","nullable":true,"description":"Workspace description"},"logoUri":{"type":"string","nullable":true,"description":"Workspace logo URI"},"teams":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"name":{"type":"string"}}}},"usageTeams":{"type":"array","description":"Active teams with workflows included in the commercial Usage scope. Internal Ops teams are excluded.","items":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"name":{"type":"string"},"totalWorkflows":{"type":"integer"},"activeSlots":{"type":"number"}}}},"memberCount":{"type":"integer","description":"Unique human members across usageTeams, or the selected team for a team workspace."}}},"error":{"type":"string","nullable":true}}}}}},"401":{"description":"Unauthorized"},"403":{"description":"Forbidden - insufficient permissions"},"404":{"description":"Workspace not found"},"500":{"description":"Internal server error"}}}},"/v5/workspaces/{workspaceId}/monthly-active":{"get":{"summary":"Recorded usage and historical Active workflow estimates","description":"Historical values come from daily usage snapshots; unavailable values are null. activeWorkflows counts ACTIVE-state workflows, while active and activeSlots count billable usage. Active billing counts real-time workflows or workflows on an enabled schedule. Today's values are computed live. active35 is retired and always null. estimatedActive is a separate display-only workflow estimate; recorded values and slot weights are unchanged. activeEstimateSource identifies calibrated historical ACTIVE counts or bounded interpolation.\n","tags":["Workspaces"],"parameters":[{"name":"workspaceId","in":"path","required":true,"description":"Workspace ID (team or organization)","schema":{"type":"string","format":"uuid"}},{"name":"days","in":"query","required":false,"description":"Number of trailing days to return (1-400, default 120).","schema":{"type":"integer"}},{"name":"x-api-key","in":"header","required":false,"schema":{"type":"string"}},{"name":"Authorization","in":"header","required":false,"schema":{"type":"string"}}],"security":[{"ApiKeyAuth":[]},{"BearerAuth":[]}],"responses":{"200":{"description":"Daily workflow and slot usage retrieved successfully","content":{"application/json":{"schema":{"type":"object","properties":{"days":{"type":"array","items":{"type":"object","properties":{"date":{"type":"string","description":"Day (UTC), YYYY-MM-DD"},"active":{"type":"integer","nullable":true,"description":"Recorded real-time or enabled scheduled workflow count; null when billing snapshots are unavailable"},"activeWorkflows":{"type":"integer","nullable":true,"description":"Recorded ACTIVE-state workflow count; null for missing snapshots"},"activeSlots":{"type":"number","format":"float","nullable":true,"description":"Recorded weighted billable slot usage; null when exact history is unavailable"},"active35":{"type":"integer","nullable":true,"description":"Retired trailing-35-day comparison; always null"},"estimatedActive":{"type":"integer","nullable":true,"description":"Display-only Active billing workflow estimate for missing history; null for recorded days or insufficient evidence"},"activeEstimateSource":{"type":"string","nullable":true,"enum":["historical_active","interpolated"],"description":"Estimate method; null when estimatedActive is null"}}}}}}}}},"400":{"description":"Bad request"},"401":{"description":"Unauthorized"},"403":{"description":"Forbidden - insufficient permissions"},"404":{"description":"Workspace not found"},"500":{"description":"Internal server error"}}}},"/v5/workspaces/{workspaceId}/observability":{"get":{"summary":"Get observability run metrics for a workspace","description":"Returns per-workflow reliability for enterprise workspaces over the last N UTC calendar days\nincluding today. The top level covers scheduled workflows (success rate, records delivered,\nmean time to recover, lifecycles) and the workspace's tickets. `realtime` covers\nrealtime monitors (measured uptime, incidents and current status, paused ones included) and\nis null when the workspace has none. Complete days come from a daily aggregate; today is\ncomputed live. Workflow lifecycles come from stored per-workflow milestones advanced with\nthe audit rows written since the nightly pass.\n","tags":["Workspaces"],"parameters":[{"name":"workspaceId","in":"path","required":true,"description":"Workspace ID (team or organization)","schema":{"type":"string","format":"uuid"}},{"name":"days","in":"query","required":false,"description":"Time range for observability data, in days (1-365)","schema":{"type":"string","default":30}},{"name":"x-api-key","in":"header","required":false,"schema":{"type":"string"}},{"name":"Authorization","in":"header","required":false,"schema":{"type":"string"}}],"security":[{"ApiKeyAuth":[]},{"BearerAuth":[]}],"responses":{"200":{"description":"Observability data retrieved successfully"},"400":{"description":"Bad request - invalid parameters"},"401":{"description":"Unauthorized"},"404":{"description":"Workspace not found or not an enterprise workspace"},"500":{"description":"Internal server error"}}}},"/v5/workspaces/{workspaceId}/period-series":{"get":{"summary":"Daily per-billing-period cumulative series for Approved workflows and extracted rows (teams and organizations)","description":"For each of the last N days, the Approved-workflow count, weighted slot usage, and extracted-row sum accumulated since the start of the billing period that day falls in, resetting at each renewal anniversary (a sawtooth across renewals). approved = distinct workflows with at least one FINISHED non-preview run in [periodStart(day), day]; approvedSlots sums their multipliers; rows sums total_records. The series is run-fact-based, so it are drift-free and fully backfilled. At today, approved equals currentContractActiveWorkflows and rows equals currentPeriodExtractedRows from the quotas endpoint.\n","tags":["Workspaces"],"parameters":[{"name":"workspaceId","in":"path","required":true,"description":"Workspace ID (team or organization)","schema":{"type":"string","format":"uuid"}},{"name":"days","in":"query","required":false,"description":"Number of trailing days to return (1-400, default 400 so at least one renewal reset is visible).","schema":{"type":"integer"}},{"name":"x-api-key","in":"header","required":false,"schema":{"type":"string"}},{"name":"Authorization","in":"header","required":false,"schema":{"type":"string"}}],"security":[{"ApiKeyAuth":[]},{"BearerAuth":[]}],"responses":{"200":{"description":"Period-cumulative daily history retrieved successfully","content":{"application/json":{"schema":{"type":"object","properties":{"days":{"type":"array","items":{"type":"object","properties":{"date":{"type":"string","description":"Day (UTC), YYYY-MM-DD"},"approved":{"type":"integer","description":"Distinct workflows that ran (FINISHED, non-preview) since the start of that day's billing period"},"approvedSlots":{"type":"number","format":"float","description":"Weighted slot usage for approved"},"rows":{"type":"integer","description":"Extracted rows (sum of total_records) for those in-period runs up to that day"}}}}}}}}},"400":{"description":"Bad request"},"401":{"description":"Unauthorized"},"403":{"description":"Forbidden - insufficient permissions"},"404":{"description":"Workspace not found"},"500":{"description":"Internal server error"}}}},"/v5/workspaces/{workspaceId}/quotas":{"get":{"summary":"Get workspace quotas and usage (supports teams and organizations)","tags":["Workspaces"],"parameters":[{"name":"workspaceId","in":"path","required":true,"description":"Workspace ID (team or organization)","schema":{"type":"string","format":"uuid"}},{"name":"x-api-key","in":"header","required":false,"description":"API key for authorization","schema":{"type":"string"}},{"name":"Authorization","in":"header","required":false,"description":"Bearer token for authorization","schema":{"type":"string"}}],"security":[{"ApiKeyAuth":[]},{"BearerAuth":[]}],"responses":{"200":{"description":"Workspace quotas retrieved successfully","content":{"application/json":{"schema":{"type":"object","properties":{"workspace":{"type":"object","properties":{"id":{"type":"string","format":"uuid","description":"Workspace ID"},"type":{"type":"string","enum":["team","organization"],"description":"Workspace type"},"billingType":{"type":"string","nullable":true,"enum":["enterprise_active","enterprise_approved"],"description":"The org-level billing model. Active is the default; null for standalone teams."},"availableQuotas":{"type":"object","properties":{"activeWorkflows":{"type":"integer","description":"Maximum allowed active workflows"},"maxExtractedRows":{"type":"integer","description":"Maximum allowed extracted rows"}}},"usedQuotas":{"type":"object","properties":{"currentTotalWorkflows":{"type":"integer","description":"Current non-deleted workflows in the workspace's commercial scope."},"currentActiveWorkflows":{"type":"integer","description":"Current number of workflows in ACTIVE state (legacy count)"},"currentBillingActiveWorkflows":{"type":"integer","description":"Active billing count. ACTIVE workflows attached to an enabled schedule, plus ACTIVE realtime workflows."},"currentBillingActiveSlots":{"type":"number","format":"float","description":"Weighted slot usage for currentBillingActiveWorkflows."},"currentApprovedWorkflows":{"type":"integer","description":"Workflows that have at least one successful non-preview run AND are alive (or were deleted within the current billing period). Billing Type 3 (per-contract). KAD-6720."},"currentScheduledWorkflows":{"type":"integer","description":"Compatibility alias for currentBillingActiveWorkflows."},"currentActive35Workflows":{"type":"integer","description":"Active-35. Distinct workflows that ran successfully (non-preview) in the trailing 35 days via any trigger (our scheduler, the client's API cron, or a manual run), OR are a live real-time monitor. The \"recent usage\" billing model; 35 days so monthly-cadence workflows don't flicker. KAD-7956."},"currentContractActiveWorkflows":{"type":"integer","nullable":true,"description":"Contract active. Distinct workflows that ran successfully (non-preview) at least once during the current contract period. The cumulative \"used this term\" billing model. Same definition as the billable-workflows list count. Null when there's no billing period (trial / no renewal_date)."},"currentContractActiveSlots":{"type":"number","format":"float","nullable":true,"description":"Weighted slot usage for currentContractActiveWorkflows."},"previousContractActiveWorkflows":{"type":"integer","nullable":true,"description":"Contract active for the PREVIOUS billing period (one cycle back). Same definition as currentContractActiveWorkflows; used for renewal sizing comparisons. Null when there's no billing period."},"previousContractActiveSlots":{"type":"number","format":"float","nullable":true,"description":"Weighted slot usage for previousContractActiveWorkflows."},"currentExtractedRows":{"type":"integer","description":"All-time cumulative extracted rows (latest team_ledger snapshot)."},"currentPeriodExtractedRows":{"type":"integer","nullable":true,"description":"Extracted rows attributed to FINISHED non-preview runs inside the current billing period. The \"by billing period\" companion to the all-time currentExtractedRows. Null when there's no billing period."}}},"billingPeriod":{"type":"object","nullable":true,"description":"The billing period the used-quota counts apply to. Enterprise uses the org's renewal_date (auto-rolled forward when stale); self-service uses the team owner's Stripe period. Null for a renewal-anchored workspace (enterprise/org) with no renewal_date — e.g. a trial — in which case the period-scoped counts above are also null.","properties":{"start":{"type":"string","format":"date-time"},"end":{"type":"string","format":"date-time"},"renewalDate":{"type":"string","format":"date","nullable":true,"description":"The org's contractual renewal date (YYYY-MM-DD), or null if not set."}}},"previousBillingPeriod":{"type":"object","nullable":true,"description":"The billing period immediately before billingPeriod (the prior contract cycle). Null when the precise counts couldn't be computed.","properties":{"start":{"type":"string","format":"date-time"},"end":{"type":"string","format":"date-time"}}}}},"error":{"type":"string","nullable":true}}}}}},"401":{"description":"Unauthorized"},"403":{"description":"Forbidden - insufficient permissions"},"404":{"description":"Workspace not found"},"500":{"description":"Internal server error"}}}},"/v5/workspaces/{workspaceId}/usage":{"get":{"summary":"Get workspace usage data (supports teams and organizations)","tags":["Workspaces"],"parameters":[{"name":"workspaceId","in":"path","required":true,"description":"Workspace ID (team or organization)","schema":{"type":"string","format":"uuid"}},{"name":"resultRange","in":"query","required":false,"description":"Time range for usage data, in days (1-365)","schema":{"type":"string","default":30}},{"name":"x-api-key","in":"header","required":false,"description":"API key for authorization","schema":{"type":"string"}},{"name":"Authorization","in":"header","required":false,"description":"Bearer token for authorization","schema":{"type":"string"}}],"security":[{"ApiKeyAuth":[]},{"BearerAuth":[]}],"responses":{"200":{"description":"Workspace usage data retrieved successfully","content":{"application/json":{"schema":{"type":"array","items":{"type":"object","properties":{"date":{"type":"string","format":"date","description":"Date in YYYY-MM-DD format"},"activeWorkflows":{"type":"integer","description":"Number of active workflows on this date"},"extractedRows":{"type":"integer","description":"Number of extracted rows on this date"}}}}}}},"400":{"description":"Bad request - invalid parameters"},"401":{"description":"Unauthorized"},"403":{"description":"Forbidden - insufficient permissions"},"404":{"description":"Workspace not found"},"500":{"description":"Internal server error"}}}},"/v4/crawl/config":{"post":{"description":"Create a new crawling configuration","summary":"Create config","tags":["Crawler"],"parameters":[],"requestBody":{"description":"Body","content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateCrawlerConfigRequest"}}}},"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateCrawlerConfigResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]},"delete":{"description":"Delete a crawling configuration","summary":"Delete config","tags":["Crawler"],"parameters":[],"requestBody":{"description":"Body","content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeleteCrawlerConfigRequest"}}}},"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeleteCrawlerConfigResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/crawl/config/{configId}":{"get":{"description":"Get a crawling configuration by ID","summary":"Get config","tags":["Crawler"],"parameters":[{"name":"configId","in":"path","required":true,"schema":{"type":"string"}}],"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/GetCrawlerConfigResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/crawl/":{"post":{"description":"Create a crawling configuration and start a session in one operation (equivalent to v4/crawl)","summary":"Start crawl","tags":["Crawler"],"parameters":[],"requestBody":{"description":"Body","content":{"application/json":{"schema":{"$ref":"#/components/schemas/StartCrawlerSessionRequest"}}}},"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/StartCrawlerSessionResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/crawl/start":{"post":{"description":"Start a new crawling session with an existing configuration","summary":"Start session","tags":["Crawler"],"parameters":[],"requestBody":{"description":"Body","content":{"application/json":{"schema":{"$ref":"#/components/schemas/StartSessionWithConfigRequest"}}}},"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/StartCrawlerSessionResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/crawl/pause":{"post":{"description":"Pause an active crawling session","summary":"Pause session","tags":["Crawler"],"parameters":[],"requestBody":{"description":"Body","content":{"application/json":{"schema":{"$ref":"#/components/schemas/PauseCrawlerSessionRequest"}}}},"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/PauseCrawlerSessionResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/crawl/resume":{"post":{"description":"Resume a paused crawling session","summary":"Resume session","tags":["Crawler"],"parameters":[],"requestBody":{"description":"Body","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ResumeCrawlerSessionRequest"}}}},"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ResumeCrawlerSessionResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/crawl/{sessionId}/status":{"get":{"description":"Get the current status of a crawling session","summary":"Get session status","tags":["Crawler"],"parameters":[{"name":"sessionId","in":"path","required":true,"schema":{"type":"string"}}],"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/GetCrawlerSessionStatusResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/crawl/{sessionId}/pages":{"get":{"description":"Get a paginated list of pages for a crawling session","summary":"Get paginated session pages","tags":["Crawler"],"parameters":[{"name":"sessionId","in":"path","required":true,"schema":{"type":"string"}},{"name":"currentPage","in":"query","description":"Current page number for pagination","schema":{"type":"number","minimum":1}},{"name":"pageSize","in":"query","description":"Number of items per page for pagination","schema":{"type":"number","minimum":1}}],"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/GetCrawlerSessionPagesResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/crawl/{sessionId}/pages/{pageId}":{"get":{"description":"Get the content of a specific page from a crawling session in HTML or Markdown format","summary":"Get session page content","tags":["Crawler"],"parameters":[{"name":"sessionId","in":"path","required":true,"schema":{"type":"string"}},{"name":"pageId","in":"path","required":true,"schema":{"type":"string"}},{"name":"format","in":"query","description":"Desired format for the page data","schema":{"type":"string"}}],"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/GetCrawlerSessionPageResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/crawl/bucket/data/{filenameb64}":{"get":{"description":"Get file content from the crawling bucket (HTML or screenshot)","summary":"Get bucket data","tags":["Crawler"],"parameters":[{"name":"filenameb64","in":"path","required":true,"schema":{"type":"string"}},{"name":"Content-Type","in":"header","schema":{"type":"string","description":"MIME type of the file"}},{"name":"Cache-Control","in":"header","schema":{"type":"string","description":"Caching instructions for CDN and client-side caching"}}],"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"nullable":true,"allOf":[{"$ref":"#/components/schemas/GetCrawlerBucketDataResponse"}]}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/crawl/{sessionId}/list":{"get":{"description":"Get a complete list of all pages crawled in a session","summary":"Get session data list","tags":["Crawler"],"parameters":[{"name":"sessionId","in":"path","required":true,"schema":{"type":"string"}},{"name":"includeAll","in":"query","schema":{"type":"boolean","nullable":true}}],"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/GetCrawlerSessionDataListResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/crawl/sessions":{"get":{"description":"Get paginated list of crawling sessions with optional filtering","summary":"List crawling sessions","tags":["Crawler"],"parameters":[{"name":"page","in":"query","description":"Page number","schema":{"default":1,"type":"number","minimum":1}},{"name":"pageSize","in":"query","description":"Items per page","schema":{"default":25,"type":"number","minimum":1,"maximum":100}},{"name":"userId","in":"query","description":"Filter by user ID","schema":{"type":"string"}}],"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ListCrawlerSessionsResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/schemas/":{"get":{"description":"Retrieve all schemas accessible by the authenticated user","summary":"List all schemas","tags":["Schemas"],"parameters":[],"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SchemasListResponse"}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]},"post":{"description":"Create a new data schema with specified fields and entity type","summary":"Create new schema","tags":["Schemas"],"parameters":[],"requestBody":{"description":"Body","content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateSchemaBody"}}}},"responses":{"201":{"description":"201","content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateSchemaResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/schemas/{schemaId}":{"get":{"description":"Retrieve a specific schema by its unique identifier","summary":"Get schema by ID","tags":["Schemas"],"parameters":[{"name":"schemaId","in":"path","required":true,"schema":{"type":"string"},"description":"Schema ID"}],"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SchemaDataResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]},"put":{"description":"Update schema metadata or create a new revision with updated fields","summary":"Update existing schema","tags":["Schemas"],"parameters":[{"name":"schemaId","in":"path","required":true,"schema":{"type":"string"},"description":"Schema ID"}],"requestBody":{"description":"Body","content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateSchemaBody"}}}},"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateSchemaResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"403":{"description":"403","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]},"delete":{"description":"Delete a schema and all its revisions","summary":"Delete schema","tags":["Schemas"],"parameters":[{"name":"schemaId","in":"path","required":true,"schema":{"type":"string"},"description":"Schema ID"}],"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeleteSchemaResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"403":{"description":"403","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/scrape":{"post":{"description":"Fetch a URL through Kadoa. Defaults to smart routing (auto fetch mode and proxy), can return page content as markdown for LLM consumption, and offers a stealth proxy tier for sites that block bots.","summary":"Scrape a URL","tags":["Scrape"],"parameters":[],"requestBody":{"description":"Body","content":{"application/json":{"schema":{"type":"object","properties":{"url":{"type":"string","format":"uri"},"method":{"default":"GET","type":"string","enum":["GET","POST","PUT","DELETE","PATCH"],"description":"HTTP method. Default: GET"},"headers":{"type":"array","items":{"type":"object","properties":{"key":{"type":"string","description":"Header name"},"value":{"type":"string","description":"Header value"}},"required":["key","value"],"description":"Custom HTTP header"},"description":"Custom HTTP headers to send with the request"},"body":{"oneOf":[{"type":"object","additionalProperties":{"nullable":true}},{"type":"string"}],"description":"Request body as JSON object, or a legacy worker-specific string. Prefer rawBody when the upstream endpoint needs an exact text payload."},"rawBody":{"type":"string","description":"Exact request body text to forward to the upstream URL. Use for endpoints that reject wrapper objects or require a specific JSON/form payload string."},"location":{"type":"object","properties":{"country":{"type":"string","minLength":2,"maxLength":2,"description":"ISO 3166-1 alpha-2 country code (e.g., 'US', 'GB', 'DE')"}},"description":"Geo-targeting for proxy selection"},"timeout":{"type":"integer","minimum":1,"maximum":60000,"description":"Per-attempt timeout in milliseconds"},"overallTimeout":{"default":240000,"type":"integer","minimum":1,"maximum":240000,"description":"Wall-clock deadline for the complete scrape in milliseconds. Default and maximum: 240000"},"context":{"type":"object","properties":{"id":{"type":"string","description":"Sticky proxy session ID. Requests sharing an ID reuse the same proxy exit where the tier supports it."}},"description":"Sticky proxy session"},"captureResponses":{"type":"array","items":{"type":"string","minLength":1},"maxItems":20,"description":"Substrings matched against network response URLs (browser workers only). The worker hooks every response the page makes and returns the body of each whose URL contains any of these substrings, in `capturedResponses`. Use this to read data that arrives via XHR/fetch and is NOT in the DOM — SPA dashboards (Tableau VizQL, Power BI) where values come back in a JSON/command response. Triggers a browser worker; pair with `browserActions` (clicks/waits) to drive the requests you want captured."},"waitUntil":{"type":"string","enum":["load","domcontentloaded","networkidle","commit"],"description":"Browser-worker navigation gate. Default (omitted) is `domcontentloaded` + a bounded best-effort networkidle settle, which returns content even on heavy pages that never go fully idle (ASP.NET, SignalR, ad/telemetry-heavy). Set `networkidle` to block the whole navigation on full idle (old behavior — only when the page reliably goes idle and you need every lazy request). No-op for non-browser workers."},"settleMs":{"type":"integer","minimum":1,"description":"Browser-worker cap (ms) for the best-effort networkidle settle after `domcontentloaded`. Default 15000. Raise for slow client-rendered pages that need more time for lazy content; lower to return faster. Ignored when `waitUntil: networkidle` and for non-browser workers."},"device":{"type":"string","description":"Device to emulate, by descriptor name (e.g. 'iPad', 'iPhone 13'). Honored by workers that support device emulation; ignored by the rest. Some sites only serve content for a given device profile."},"fetchMode":{"default":"auto","type":"string","enum":["http","browser","auto"],"description":"Fetch mode: http for fast requests, browser for JavaScript rendering and browser actions, or auto for smart routing that starts cheap and escalates when blocked. Default: auto"},"proxy":{"default":"auto","type":"string","enum":["auto","direct","dc","isp","residential","stealth"],"description":"Proxy tier: auto (smart selection), direct (Squid server egress without location guarantees), dc (datacenter), isp, residential, or stealth to route through the anti-bot providers for sites that block bots. Stealth providers use their own egress and pricing. Default: auto"},"format":{"default":"html","type":"string","enum":["html","markdown"],"description":"Content format for HTML pages. markdown converts the page to markdown with navigation, header, and footer stripped — the compact shape to feed an LLM. Non-HTML responses (JSON, binary) and HTML pages over 2 MB are returned unchanged; check the response contentType to see which format was applied. Default: html"},"browserActions":{"type":"array","items":{"discriminator":{"propertyName":"type"},"oneOf":[{"type":"object","properties":{"type":{"type":"string","enum":["click"],"description":"Action type"},"selector":{"type":"object","properties":{"type":{"type":"string","enum":["xpath","css","text"],"description":"Selector type"},"value":{"type":"string","description":"Selector value (e.g., '#submit-btn' for CSS, '//button[@type=\"submit\"]' for XPath)"}},"required":["type","value"],"description":"Element to click"}},"required":["type","selector"],"title":"click","description":"Click an element on the page"},{"type":"object","properties":{"type":{"type":"string","enum":["input"],"description":"Action type"},"selector":{"type":"object","properties":{"type":{"type":"string","enum":["xpath","css","text"],"description":"Selector type"},"value":{"type":"string","description":"Selector value (e.g., '#submit-btn' for CSS, '//button[@type=\"submit\"]' for XPath)"}},"required":["type","value"],"description":"Input element to type into"},"value":{"type":"string","description":"Text to type into the element"}},"required":["type","selector","value"],"title":"input","description":"Type text into an input element"},{"type":"object","properties":{"type":{"type":"string","enum":["scroll"],"description":"Action type"},"x":{"type":"number","description":"Horizontal scroll amount in pixels"},"y":{"type":"number","description":"Vertical scroll amount in pixels"}},"required":["type","y"],"title":"scroll","description":"Scroll by a specific number of pixels"},{"type":"object","properties":{"type":{"type":"string","enum":["scroll_to_bottom"],"description":"Action type"},"timeout_s":{"type":"number","minimum":1,"maximum":300,"description":"Maximum time to scroll in seconds (default: 30, maximum: 300)"}},"required":["type"],"title":"scroll_to_bottom","description":"Scroll to the bottom of the page (useful for infinite scroll)"},{"type":"object","properties":{"type":{"type":"string","enum":["wait"],"description":"Action type"},"wait_time_s":{"type":"number","minimum":1,"maximum":300,"description":"Duration to wait in seconds (maximum: 300)"}},"required":["type","wait_time_s"],"title":"wait","description":"Wait for a specified duration"},{"type":"object","properties":{"type":{"type":"string","enum":["screenshot"],"description":"Action type"},"full_page":{"type":"boolean","description":"Capture the full page (true) or just the viewport (false)"},"format":{"default":"jpg","type":"string","enum":["jpg","png","webp"],"description":"Output image format. Default: jpg"},"quality":{"default":20,"type":"integer","minimum":1,"maximum":100,"description":"Compression quality (1-100). Only applies to jpg and webp. Ignored for png. Default: 20"},"width":{"type":"integer","minimum":1,"description":"Resize to this width in pixels (height scales proportionally). No upscaling."}},"required":["type"],"title":"screenshot","description":"Capture a screenshot of the page"},{"type":"object","properties":{"type":{"type":"string","enum":["evaluate_js"],"description":"Action type"},"script":{"type":"string","description":"JavaScript code to execute in the page context"}},"required":["type","script"],"title":"evaluate_js","description":"Execute JavaScript in the browser context"},{"type":"object","properties":{"type":{"type":"string","enum":["wait_for_element"],"description":"Action type"},"selector":{"type":"object","properties":{"type":{"type":"string","enum":["xpath","css","text"],"description":"Selector type"},"value":{"type":"string","description":"Selector value (e.g., '#submit-btn' for CSS, '//button[@type=\"submit\"]' for XPath)"}},"required":["type","value"],"description":"Element to wait for"},"timeout_s":{"type":"number","minimum":1,"maximum":300,"description":"Maximum time to wait in seconds (default: 10, maximum: 300)"}},"required":["type","selector"],"title":"wait_for_element","description":"Wait for an element to appear on the page"}],"description":"Browser action to perform on the page"},"maxItems":50}},"required":["url"],"additionalProperties":false}}}},"responses":{"200":{"description":"Scrape response with content and execution metadata","content":{"application/json":{"schema":{"type":"object","properties":{"session":{"type":"object","properties":{"id":{"type":"string"}},"required":["id"],"description":"Acknowledged browser-session handle; pass it on subsequent raw API calls."},"retryable":{"type":"boolean","description":"Whether repeating this scrape is safe and useful; absence does not authorize retry"},"retryAfterMs":{"type":"integer","minimum":0,"maximum":4294967295,"description":"Minimum delay before another scrape attempt, in milliseconds"},"success":{"type":"boolean","description":"Whether the scrape succeeded"},"contentType":{"type":"string","description":"MIME type of the response (e.g., text/html, application/json, image/png)"},"content":{"type":"string","description":"Response content (raw text for html/json, base64 for binary)"},"isBase64":{"default":false,"type":"boolean","description":"Whether content is base64-encoded (true for binary content types like PDFs, images)"},"screenshots":{"type":"array","items":{"type":"string"},"description":"URLs of captured screenshots"},"jsResults":{"type":"array","items":{"nullable":true},"description":"Results of evaluate_js actions, in order of execution. Each entry is the JSON-serializable return value, or {error: string} if the script threw."},"capturedResponses":{"type":"array","items":{"type":"object","properties":{"url":{"type":"string","description":"Full URL of the captured response"},"status":{"type":"number","description":"HTTP status code of the captured response"},"body":{"type":"string","description":"Response body as text"}},"required":["url","status","body"]},"description":"Bodies of network responses whose URL matched a `captureResponses` substring, in arrival order. Present only when `captureResponses` was set and at least one response matched."},"statusCode":{"type":"number","description":"HTTP status code from the response"},"headers":{"type":"object","additionalProperties":{"type":"string"},"description":"Response headers as key-value pairs"},"cookies":{"type":"array","items":{"type":"object","properties":{"name":{"type":"string","description":"Cookie name"},"value":{"type":"string","description":"Cookie value"},"domain":{"type":"string","description":"Cookie domain"},"path":{"type":"string","description":"Cookie path"},"expires":{"type":"number","description":"Expiration timestamp (Unix epoch)"},"httpOnly":{"type":"boolean","description":"HttpOnly flag"},"secure":{"type":"boolean","description":"Secure flag"},"sameSite":{"type":"string","enum":["Strict","Lax","None"],"description":"SameSite attribute"}},"required":["name","value"],"description":"HTTP cookie from the response"},"description":"Cookies set by the response"},"finalUrl":{"type":"string","description":"Final URL after any redirects"},"execution":{"type":"object","properties":{"requestId":{"type":"string","format":"uuid","description":"Opaque request identifier for correlating scraper API and worker lifecycle diagnostics"},"traceId":{"type":"string","pattern":"^[0-9a-f]{32}$","description":"Opaque trace identifier for retrieving sanitized scrape timing diagnostics when tracing is enabled"},"totalDurationMs":{"type":"number","description":"Total time including all retries in milliseconds"},"contextId":{"type":"string","nullable":true,"description":"Context ID used or created, if context feature was used"},"attempts":{"type":"array","items":{"type":"object","properties":{"worker":{"type":"string","enum":["http","browser","stealth-http","stealth-browser"],"description":"Worker capability used for this attempt"},"proxy":{"type":"string","enum":["direct","dc","isp","residential"],"description":"Proxy type: direct Squid egress, datacenter, ISP, or residential","nullable":true},"location":{"type":"object","properties":{"country":{"type":"string","minLength":2,"maxLength":2,"description":"ISO 3166-1 alpha-2 country code (e.g., 'US', 'GB', 'DE')"}},"description":"Location used for geo-targeting, or null","nullable":true},"startedAt":{"type":"string","format":"date-time","description":"ISO 8601 timestamp when attempt started"},"endedAt":{"type":"string","format":"date-time","description":"ISO 8601 timestamp when attempt ended"},"durationMs":{"type":"number","description":"Attempt duration in milliseconds"},"success":{"type":"boolean","description":"Whether this attempt succeeded"},"provider":{"type":"string","enum":["auto","curl-cffi","kurl","kadmium","scrape-ops","driver"],"description":"Concrete provider used for this attempt"},"error":{"type":"object","properties":{"code":{"type":"string","enum":["BOT_DETECTED","ACCESS_DENIED","TIMEOUT","JS_REQUIRED","KYC_BLOCKED","MAX_RETRIES_EXCEEDED","NETWORK_ERROR","SCREENSHOT_TOO_LARGE","DEADLINE_EXCEEDED"],"description":"Error code"},"message":{"type":"string","description":"Human-readable error message"},"appCode":{"type":"string","description":"Underlying backend application error code, when available"},"provider":{"type":"string","enum":["auto","curl-cffi","kurl","kadmium","scrape-ops","driver"],"description":"Concrete provider that produced the failure"},"cluster":{"type":"string","description":"Cluster where the failure originated"},"cause":{"type":"object","properties":{"code":{"type":"string","enum":["BOT_DETECTED","ACCESS_DENIED","TIMEOUT","JS_REQUIRED","KYC_BLOCKED","MAX_RETRIES_EXCEEDED","NETWORK_ERROR","SCREENSHOT_TOO_LARGE","DEADLINE_EXCEEDED"],"description":"Error code"},"message":{"type":"string","description":"Human-readable error message"},"appCode":{"type":"string","description":"Underlying backend application error code, when available"},"provider":{"type":"string","enum":["auto","curl-cffi","kurl","kadmium","scrape-ops","driver"],"description":"Concrete provider that produced the failure"},"cluster":{"type":"string","description":"Cluster where the failure originated"}},"required":["code","message"],"description":"Original failure when retries are exhausted"}},"required":["code","message"],"description":"Error details if attempt failed"}},"required":["worker","proxy","location","startedAt","endedAt","durationMs","success"],"description":"Details of a single scrape attempt"}}},"required":["totalDurationMs","attempts"],"description":"Execution metadata including timing and retry information"},"error":{"type":"object","properties":{"code":{"type":"string","enum":["BOT_DETECTED","ACCESS_DENIED","TIMEOUT","JS_REQUIRED","KYC_BLOCKED","MAX_RETRIES_EXCEEDED","NETWORK_ERROR","SCREENSHOT_TOO_LARGE","DEADLINE_EXCEEDED"],"description":"Error code"},"message":{"type":"string","description":"Human-readable error message"},"appCode":{"type":"string","description":"Underlying backend application error code, when available"},"provider":{"type":"string","enum":["auto","curl-cffi","kurl","kadmium","scrape-ops","driver"],"description":"Concrete provider that produced the failure"},"cluster":{"type":"string","description":"Cluster where the failure originated"},"cause":{"type":"object","properties":{"code":{"type":"string","enum":["BOT_DETECTED","ACCESS_DENIED","TIMEOUT","JS_REQUIRED","KYC_BLOCKED","MAX_RETRIES_EXCEEDED","NETWORK_ERROR","SCREENSHOT_TOO_LARGE","DEADLINE_EXCEEDED"],"description":"Error code"},"message":{"type":"string","description":"Human-readable error message"},"appCode":{"type":"string","description":"Underlying backend application error code, when available"},"provider":{"type":"string","enum":["auto","curl-cffi","kurl","kadmium","scrape-ops","driver"],"description":"Concrete provider that produced the failure"},"cluster":{"type":"string","description":"Cluster where the failure originated"}},"required":["code","message"],"description":"Original failure when retries are exhausted"}},"required":["code","message"],"description":"Error details when success is false"}},"required":["success","execution"],"description":"Scrape response with content and execution metadata"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","enum":[true]},"message":{"type":"string"},"code":{"type":"string"},"appCode":{"type":"string"},"traceId":{"type":"string"},"provider":{"type":"string"},"cluster":{"type":"string"},"details":{"type":"object","additionalProperties":{"nullable":true}}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"string"}},"required":["error"]}}}},"403":{"description":"403","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","enum":[true]},"message":{"type":"string"},"code":{"type":"string"},"appCode":{"type":"string"},"traceId":{"type":"string"},"provider":{"type":"string"},"cluster":{"type":"string"},"details":{"type":"object","additionalProperties":{"nullable":true}}},"required":["error","message"]}}}},"429":{"description":"429","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","enum":[true]},"message":{"type":"string"},"code":{"type":"string"},"appCode":{"type":"string"},"traceId":{"type":"string"},"provider":{"type":"string"},"cluster":{"type":"string"},"details":{"type":"object","additionalProperties":{"nullable":true}}},"required":["error","message"]}}}},"500":{"description":"Internal server error","content":{"application/json":{"schema":{"type":"object","properties":{"retryable":{"type":"boolean","description":"Whether repeating this scrape is safe and useful; absence does not authorize retry"},"retryAfterMs":{"type":"integer","minimum":0,"maximum":4294967295,"description":"Minimum delay before another scrape attempt, in milliseconds"},"error":{"type":"boolean","enum":[true],"description":"Always true for error responses"},"message":{"type":"string","description":"Human-readable error message"},"code":{"type":"string"},"appCode":{"type":"string"},"traceId":{"type":"string"},"provider":{"type":"string"},"cluster":{"type":"string"}},"required":["error","message"],"description":"Internal server error"}}}},"502":{"description":"502","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","enum":[true]},"message":{"type":"string"},"code":{"type":"string"},"appCode":{"type":"string"},"traceId":{"type":"string"},"provider":{"type":"string"},"cluster":{"type":"string"},"details":{"type":"object","additionalProperties":{"nullable":true}}},"required":["error","message"]}}}},"503":{"description":"The scrape backend or managed browser capacity is unavailable","content":{"application/json":{"schema":{"type":"object","properties":{"retryable":{"type":"boolean","description":"Whether repeating this scrape is safe and useful; absence does not authorize retry"},"retryAfterMs":{"type":"integer","minimum":0,"maximum":4294967295,"description":"Minimum delay before another scrape attempt, in milliseconds"},"error":{"type":"boolean","enum":[true]},"code":{"type":"string","enum":["SCRAPE_BACKEND_UNAVAILABLE","BROWSER_CAPACITY_UNAVAILABLE"]},"appCode":{"type":"string"},"message":{"type":"string"},"traceId":{"type":"string"},"provider":{"type":"string"},"cluster":{"type":"string"}},"required":["error","code","message"],"description":"The scrape backend or managed browser capacity is unavailable"}}}},"504":{"description":"504","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","enum":[true]},"message":{"type":"string"},"code":{"type":"string"},"appCode":{"type":"string"},"traceId":{"type":"string"},"provider":{"type":"string"},"cluster":{"type":"string"},"details":{"type":"object","additionalProperties":{"nullable":true}}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/templates/":{"get":{"description":"List all active templates for the authenticated user's team","summary":"List all templates","tags":["Templates"],"parameters":[],"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/TemplateListResponse"}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]},"post":{"description":"Create a new template for the team","summary":"Create new template","tags":["Templates"],"parameters":[],"requestBody":{"description":"Body","content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateTemplateBody"}}}},"responses":{"201":{"description":"201","content":{"application/json":{"schema":{"$ref":"#/components/schemas/TemplateCreatedResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"409":{"description":"409","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/templates/{templateId}":{"get":{"description":"Retrieve a template with all its published versions","summary":"Get template by ID","tags":["Templates"],"parameters":[{"name":"templateId","in":"path","required":true,"schema":{"type":"string","format":"uuid"},"description":"Template ID"}],"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/TemplateDetailResponseBody"}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]},"put":{"description":"Update template name or description","summary":"Update template","tags":["Templates"],"parameters":[{"name":"templateId","in":"path","required":true,"schema":{"type":"string","format":"uuid"},"description":"Template ID"}],"requestBody":{"description":"Body","content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateTemplateBody"}}}},"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/TemplateUpdatedResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"409":{"description":"409","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]},"delete":{"description":"Soft-delete (archive) a template and cascade-unlink any workflows that referenced it.","summary":"Archive template","tags":["Templates"],"parameters":[{"name":"templateId","in":"path","required":true,"schema":{"type":"string","format":"uuid"},"description":"Template ID"}],"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/TemplateArchivedResponse"}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/templates/{templateId}/duplicate":{"post":{"description":"Create an independent copy of a template from its latest published version as a single new version 1, including prompt, schema, validation rules, notifications, and frequency. The copy has no linked workflows. Defaults the name to the source name plus a collision-safe \"(Copy)\" suffix.","summary":"Duplicate template","tags":["Templates"],"parameters":[{"name":"templateId","in":"path","required":true,"schema":{"type":"string","format":"uuid"},"description":"Template ID"}],"requestBody":{"description":"Body","content":{"application/json":{"schema":{"$ref":"#/components/schemas/DuplicateTemplateBody"}}}},"responses":{"201":{"description":"201","content":{"application/json":{"schema":{"$ref":"#/components/schemas/TemplateCreatedResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"409":{"description":"409","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/templates/{templateId}/versions":{"post":{"description":"Create a new immutable version of a template with prompt, schema, and/or data validation","summary":"Publish template version","tags":["Templates"],"parameters":[{"name":"templateId","in":"path","required":true,"schema":{"type":"string","format":"uuid"},"description":"Template ID"}],"requestBody":{"description":"Body","content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateTemplateVersionBody"}}}},"responses":{"201":{"description":"201","content":{"application/json":{"schema":{"$ref":"#/components/schemas/TemplateVersionMutationResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/templates/{templateId}/versions/{version}":{"patch":{"description":"Set or clear the display name of a published template version. The version content stays immutable; only the label changes.","summary":"Rename template version","tags":["Templates"],"parameters":[{"name":"templateId","in":"path","required":true,"schema":{"type":"string","format":"uuid"},"description":"Template ID"},{"name":"version","in":"path","required":true,"schema":{"type":"integer","minimum":1},"description":"Template version number"}],"requestBody":{"description":"Body","content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateTemplateVersionBody"}}}},"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/TemplateVersionMutationResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/templates/{templateId}/schemas":{"get":{"description":"List all schemas linked to this template","summary":"List template schemas","tags":["Templates"],"parameters":[{"name":"templateId","in":"path","required":true,"schema":{"type":"string","format":"uuid"},"description":"Template ID"}],"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/TemplateSchemasResponse"}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/templates/{templateId}/workflows":{"get":{"description":"List all workflows created from this template (isOutdated flag is informational-only in v1 — applyUpdate is disabled)","summary":"List template workflows","tags":["Templates"],"parameters":[{"name":"templateId","in":"path","required":true,"schema":{"type":"string","format":"uuid"},"description":"Template ID"}],"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/TemplateWorkflowsResponse"}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/templates/{templateId}/apply":{"post":{"description":"Apply a template version's config to existing workflows (clone with lineage update)","summary":"Apply template update","tags":["Templates"],"parameters":[{"name":"templateId","in":"path","required":true,"schema":{"type":"string","format":"uuid"},"description":"Template ID"}],"requestBody":{"description":"Body","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApplyTemplateUpdateBody"}}}},"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApplyTemplateUpdateResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/templates/{templateId}/preview-schema-change":{"post":{"description":"Preview the data a schema change would produce for one linked workflow, without applying the template or running the workflow","summary":"Preview schema change","tags":["Templates"],"parameters":[{"name":"templateId","in":"path","required":true,"schema":{"type":"string","format":"uuid"},"description":"Template ID"}],"requestBody":{"description":"Body","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SchemaChangePreviewBody"}}}},"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SchemaChangePreviewResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/templates/{templateId}/link":{"post":{"description":"Associate existing workflows with this template at the latest version. Returns 409 with conflict details if workflows are linked to another template (use force: true to override).","summary":"Link workflows to template","tags":["Templates"],"parameters":[{"name":"templateId","in":"path","required":true,"schema":{"type":"string","format":"uuid"},"description":"Template ID"}],"requestBody":{"description":"Body","content":{"application/json":{"schema":{"$ref":"#/components/schemas/LinkWorkflowsBody"}}}},"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/LinkWorkflowsResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"409":{"description":"409","content":{"application/json":{"schema":{"$ref":"#/components/schemas/LinkWorkflowsConflictResponse"}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/templates/from-workflow":{"post":{"description":"Extract a workflow's prompt, schema, validation rules, and notifications into a new template or as a new version of an existing template. The source workflow is not modified (v1: no auto-link).","summary":"Save workflow as template","tags":["Templates"],"parameters":[],"requestBody":{"description":"Body","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SaveFromWorkflowBody"}}}},"responses":{"201":{"description":"201","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SaveFromWorkflowResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"409":{"description":"409","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/templates/{templateId}/unlink":{"post":{"description":"Remove the template association from workflows (does not change workflow config)","summary":"Unlink workflows from template","tags":["Templates"],"parameters":[{"name":"templateId","in":"path","required":true,"schema":{"type":"string","format":"uuid"},"description":"Template ID"}],"requestBody":{"description":"Body","content":{"application/json":{"schema":{"$ref":"#/components/schemas/UnlinkWorkflowsBody"}}}},"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/UnlinkWorkflowsResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/workflows/{workflowId}/jobs/{jobId}":{"get":{"description":"Retrieve the current status and telemetry information for a specific job","summary":"Get job status and telemetry","tags":["Workflows"],"parameters":[{"name":"workflowId","in":"path","required":true,"schema":{"type":"string"},"description":"The ID of the workflow"},{"name":"jobId","in":"path","required":true,"schema":{"type":"string"},"description":"The ID of the job"}],"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/JobStatusResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"$ref":"#/components/schemas/JobStatusErrorResponse"}}}},"401":{"description":"401","content":{"application/json":{"schema":{"$ref":"#/components/schemas/JobStatusErrorResponse"}}}},"404":{"description":"404","content":{"application/json":{"schema":{"$ref":"#/components/schemas/JobStatusErrorResponse"}}}},"500":{"description":"500","content":{"application/json":{"schema":{"$ref":"#/components/schemas/JobStatusErrorResponse"}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/activity/workflows/export":{"get":{"description":"Export workflow configurations and metadata as CSV for portfolio reviews and compliance reporting. Includes notification channel details.","summary":"Export workflow metadata","tags":["Activity"],"parameters":[{"name":"timeFilter","in":"query","description":"Time range filter for workflow export","schema":{"default":"all-time","type":"string","enum":["last-week","last-month","last-6-months","all-time"]}}],"responses":{"200":{"description":"200"},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"403":{"description":"403","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/activity/":{"get":{"description":"Retrieve activity events from audit_logs table with basic filtering and pagination.","summary":"List activity events (new implementation)","tags":["Activity"],"parameters":[{"name":"limit","in":"query","schema":{"default":100,"type":"integer","minimum":1,"maximum":1000}},{"name":"offset","in":"query","schema":{"default":0,"type":"integer","minimum":0,"nullable":true}},{"name":"workflowId","in":"query","schema":{"type":"string","minLength":1}},{"name":"userId","in":"query","schema":{"type":"string","minLength":1}},{"name":"startDate","in":"query","schema":{"type":"string","format":"date-time","nullable":true}},{"name":"endDate","in":"query","schema":{"type":"string","format":"date-time","nullable":true}},{"name":"relativeTime","in":"query","description":"Relative time window counted backwards from now (e.g., 6h, 1d, 2w)","schema":{"type":"string","pattern":"^\\d+(m|h|d|w)$"}},{"name":"eventTypes","in":"query","description":"Comma-separated list of event types to filter by","schema":{"type":"string"}},{"name":"interfaces","in":"query","description":"Comma-separated list of request sources to filter by (e.g., SYSTEM, UI, SDK, API) - filters by requestSource field","schema":{"type":"string"}},{"name":"resourceTypes","in":"query","description":"Comma-separated list of resource types to filter by (e.g., WORKFLOW, DATA_QUALITY_RULE, SCHEMA, NOTIFICATION_CHANNEL)","schema":{"type":"string"}}],"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ActivityListResponse"}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"403":{"description":"403","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/activity/export":{"get":{"description":"Export activity events from audit_logs table to CSV format for compliance and audit purposes.","summary":"Export activity events as CSV (new implementation)","tags":["Activity"],"parameters":[{"name":"limit","in":"query","schema":{"type":"integer","minimum":1}},{"name":"offset","in":"query","schema":{"default":0,"type":"integer","minimum":0,"nullable":true}},{"name":"workflowId","in":"query","schema":{"type":"string","minLength":1}},{"name":"userId","in":"query","schema":{"type":"string","minLength":1}},{"name":"startDate","in":"query","schema":{"type":"string","format":"date-time","nullable":true}},{"name":"endDate","in":"query","schema":{"type":"string","format":"date-time","nullable":true}},{"name":"relativeTime","in":"query","description":"Relative time window counted backwards from now (e.g., 6h, 1d, 2w)","schema":{"type":"string","pattern":"^\\d+(m|h|d|w)$"}},{"name":"eventTypes","in":"query","schema":{"type":"string"}},{"name":"interfaces","in":"query","schema":{"type":"string"}},{"name":"resourceTypes","in":"query","schema":{"type":"string"}}],"responses":{"200":{"description":"200"},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"403":{"description":"403","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/user/onboarding":{"post":{"description":"Complete user onboarding process, update profile, and send welcome email","summary":"Finish onboarding","tags":["User"],"parameters":[],"requestBody":{"description":"Body","content":{"application/json":{"schema":{"type":"object","properties":{"name":{"type":"string","description":"User's full name"},"company":{"type":"string","description":"User's company name"},"jobTitle":{"type":"string","description":"User's job title"},"useCase":{"type":"string","description":"Primary use case for the product"},"useCaseOther":{"type":"string","description":"Other use case if not listed"},"usageType":{"type":"string","description":"Type of usage"},"useCaseDetails":{"type":"string","description":"Additional details about use case"},"jobLevel":{"type":"string","description":"User's job level"}}}}}},"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"type":"object","properties":{"success":{"type":"boolean","description":"Whether the onboarding was successful"},"error":{"type":"string","description":"Error message if onboarding failed"}},"required":["success"]}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/me/features":{"get":{"description":"Return the capabilities enabled for the authenticated team. Clients (such as the Kadoa MCP) use this to decide which tools to expose.","summary":"Get enabled capabilities","tags":["Me"],"parameters":[],"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"type":"object","properties":{"features":{"type":"object","properties":{"scrape":{"type":"boolean","description":"Whether this team may call POST /v4/scrape (the Scrape API)."}},"required":["scrape"],"description":"Capabilities enabled for the authenticated team."},"defaultProductType":{"type":"string","enum":["realtime","workflow"],"description":"The product this team creates by default when a request does not name one: realtime monitoring or a one-time/scheduled workflow."}},"required":["features","defaultProductType"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/variables/connections":{"get":{"summary":"List secret provider connections","tags":["Variables"],"parameters":[],"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"type":"object","properties":{"connections":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"displayName":{"type":"string"},"provider":{"type":"string","enum":["GOOGLE_SECRET_MANAGER"]},"authMode":{"type":"string","enum":["CUSTOMER_GRANT","SERVICE_ACCOUNT"]},"status":{"type":"string","enum":["CONNECTED","NEEDS_ATTENTION"]},"projectId":{"type":"string"},"brokerPrincipal":{"type":"string"},"serviceAccountEmail":{"type":"string","format":"email"},"verifiedAt":{"type":"string"},"createdAt":{"type":"string"},"updatedAt":{"type":"string"}},"required":["id","displayName","provider","authMode","status","projectId","createdAt","updatedAt"]}},"error":{"type":"string","nullable":true}},"required":["connections","error"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"403":{"description":"403","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"503":{"description":"503","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]},"post":{"summary":"Create and verify a Google Secret Manager connection","tags":["Variables"],"parameters":[],"requestBody":{"description":"Body","content":{"application/json":{"schema":{"discriminator":{"propertyName":"authMode"},"oneOf":[{"type":"object","properties":{"displayName":{"type":"string","minLength":1},"projectId":{"type":"string","minLength":1},"authMode":{"type":"string","enum":["CUSTOMER_GRANT"]}},"required":["displayName","projectId","authMode"]},{"type":"object","properties":{"displayName":{"type":"string","minLength":1},"authMode":{"type":"string","enum":["SERVICE_ACCOUNT"]},"serviceAccountJson":{"type":"string","minLength":1,"description":"Write-only service-account JSON"}},"required":["displayName","authMode","serviceAccountJson"]}]}}}},"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"type":"object","properties":{"connection":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"displayName":{"type":"string"},"provider":{"type":"string","enum":["GOOGLE_SECRET_MANAGER"]},"authMode":{"type":"string","enum":["CUSTOMER_GRANT","SERVICE_ACCOUNT"]},"status":{"type":"string","enum":["CONNECTED","NEEDS_ATTENTION"]},"projectId":{"type":"string"},"brokerPrincipal":{"type":"string"},"serviceAccountEmail":{"type":"string","format":"email"},"verifiedAt":{"type":"string"},"createdAt":{"type":"string"},"updatedAt":{"type":"string"}},"required":["id","displayName","provider","authMode","status","projectId","createdAt","updatedAt"],"nullable":true},"error":{"type":"string","nullable":true}},"required":["connection","error"]}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"403":{"description":"403","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"503":{"description":"503","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/variables/connections/{connectionId}":{"patch":{"summary":"Reconnect a Google Secret Manager connection","tags":["Variables"],"parameters":[{"name":"connectionId","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"requestBody":{"description":"Body","content":{"application/json":{"schema":{"type":"object","properties":{"displayName":{"type":"string","minLength":1},"projectId":{"type":"string","minLength":1},"serviceAccountJson":{"type":"string","minLength":1,"description":"Replacement write-only credential"}},"required":["displayName"]}}}},"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"type":"object","properties":{"connection":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"displayName":{"type":"string"},"provider":{"type":"string","enum":["GOOGLE_SECRET_MANAGER"]},"authMode":{"type":"string","enum":["CUSTOMER_GRANT","SERVICE_ACCOUNT"]},"status":{"type":"string","enum":["CONNECTED","NEEDS_ATTENTION"]},"projectId":{"type":"string"},"brokerPrincipal":{"type":"string"},"serviceAccountEmail":{"type":"string","format":"email"},"verifiedAt":{"type":"string"},"createdAt":{"type":"string"},"updatedAt":{"type":"string"}},"required":["id","displayName","provider","authMode","status","projectId","createdAt","updatedAt"],"nullable":true},"error":{"type":"string","nullable":true}},"required":["connection","error"]}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"403":{"description":"403","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"503":{"description":"503","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]},"delete":{"summary":"Delete an unused secret provider connection","tags":["Variables"],"parameters":[{"name":"connectionId","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"string","nullable":true}},"required":["error"]}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"403":{"description":"403","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"503":{"description":"503","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/variables/connections/{connectionId}/verify":{"post":{"summary":"Retry secret provider connection verification","tags":["Variables"],"parameters":[{"name":"connectionId","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"string","nullable":true}},"required":["error"]}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"403":{"description":"403","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"503":{"description":"503","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/variables/":{"post":{"description":"Create a new key-value variable. Keys must be unique within the team/user scope. Variables can be referenced in workflow prompts using @variableKey syntax.","summary":"Create a variable","tags":["Variables"],"parameters":[],"requestBody":{"description":"Body","content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateVariableBody"}}}},"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/VariableResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"403":{"description":"403","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"409":{"description":"409","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"503":{"description":"503","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]},"get":{"description":"Retrieve all variables in the current team/user scope (max 100).","summary":"List all variables","tags":["Variables"],"parameters":[],"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/VariablesListResponse"}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"403":{"description":"403","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}},"/v4/variables/{variableId}":{"get":{"description":"Retrieve a specific variable by its ID.","summary":"Get a variable","tags":["Variables"],"parameters":[{"name":"variableId","in":"path","required":true,"schema":{"type":"string"},"description":"Variable ID"}],"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/VariableResponse"}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"403":{"description":"403","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]},"patch":{"description":"Update an existing variable. At least one field (key, value, or dataType) must be provided.","summary":"Update a variable","tags":["Variables"],"parameters":[{"name":"variableId","in":"path","required":true,"schema":{"type":"string"},"description":"Variable ID"}],"requestBody":{"description":"Body","content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateVariableBody"}}}},"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/VariableResponse"}}}},"400":{"description":"400","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"403":{"description":"403","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"409":{"description":"409","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"503":{"description":"503","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]},"delete":{"description":"Permanently delete a variable by its ID. A secret bound to a connector returns 409 Conflict.","summary":"Delete a variable","tags":["Variables"],"parameters":[{"name":"variableId","in":"path","required":true,"schema":{"type":"string"},"description":"Variable ID"}],"responses":{"200":{"description":"200","content":{"application/json":{"schema":{"$ref":"#/components/schemas/VariableResponse"}}}},"401":{"description":"401","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"403":{"description":"403","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"404":{"description":"404","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"409":{"description":"409","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"500":{"description":"500","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}},"503":{"description":"503","content":{"application/json":{"schema":{"type":"object","properties":{"error":{"type":"boolean","description":"Indicates an error occurred"},"message":{"type":"string","description":"Error message"},"details":{"nullable":true,"description":"Additional error details (e.g., validation errors)"}},"required":["error","message"]}}}}},"security":[{"ApiKeyAuth":[]}]}}},"components":{"schemas":{"WorkflowAssistantState":{"type":"object","required":["status","lastSettlement"],"properties":{"status":{"type":"string","enum":["ready","running","awaiting_input","interrupted","error","aborted"]},"lastSettlement":{"type":"object","nullable":true,"description":"Last recorded customer-thread settlement; null for historical threads without this evidence. Private work never overwrites it.","required":["status","at"],"properties":{"status":{"type":"string"},"at":{"type":"string","format":"date-time"},"hasFailure":{"type":"boolean"}}}}},"WorkflowPresentation":{"type":"object","description":"The status selects one operational notice. Badges separate lifecycle, activity and binary support ownership. Published data remains available independently.","required":["status","badges","group"],"properties":{"status":{"type":"string","enum":["DRAFT","ERROR","PAUSED","NOT_SUPPORTED","PREVIEW","QUEUED","SETUP","PENDING_START","RUNNING","FAILED","COMPLIANCE_REVIEW","COMPLIANCE_REJECTED","DEGRADED","DELETED","STOPPED","COMPLETE","SCHEDULED","UPDATING","AWAITING_REVIEW","REPLY_NEEDED","UPDATE_FAILED"]},"badges":{"type":"array","items":{"type":"object","required":["kind","status"],"properties":{"kind":{"type":"string","enum":["lifecycle","activity","support"]},"status":{"type":"string","enum":["DRAFT","ERROR","PAUSED","NOT_SUPPORTED","PREVIEW","QUEUED","SETUP","PENDING_START","RUNNING","FAILED","COMPLIANCE_REVIEW","COMPLIANCE_REJECTED","DEGRADED","DELETED","STOPPED","COMPLETE","SCHEDULED","UPDATING","AWAITING_REVIEW","REPLY_NEEDED","UPDATE_FAILED","ASSISTANT_WORKING","IN_SUPPORT"]}}}},"group":{"type":"string","enum":["attention","working","support","failed","active","complete","paused"]}}},"WorkflowExecutionState":{"type":"object","required":["phase","inProgress","previewAvailable","updating"],"properties":{"phase":{"type":"string","nullable":true,"enum":["RUNNING","VALIDATING","FINISHED","FAILED","STOPPED",null]},"inProgress":{"type":"boolean"},"previewAvailable":{"type":"boolean","description":"A finished published preview exists, including empty results. Independent of new runs or workspace activity."},"updating":{"type":"boolean","description":"Workflow execution or assistant/repair work is in progress."}}},"WorkflowActionAvailability":{"oneOf":[{"type":"object","required":["allowed"],"properties":{"allowed":{"type":"boolean","enum":[true]}}},{"type":"object","required":["allowed","reason"],"properties":{"allowed":{"type":"boolean","enum":[false]},"reason":{"type":"string","enum":["ASSISTANT_ACTIVE","REPAIR_ACTIVE","RUN_IN_PROGRESS","INITIAL_SETUP","NOT_IN_PREVIEW","NO_RUNNING_JOB","WORKFLOW_UNAVAILABLE"]}}}]},"WorkflowAvailableActions":{"type":"object","description":"Customer lifecycle eligibility at read time. Authorization, quotas, template restrictions and mutation-time validation still apply. This is not an execution reservation.","required":["approve","rerun","run","pause","resume","edit","stop","delete"],"properties":{"approve":{"$ref":"#/components/schemas/WorkflowActionAvailability"},"run":{"$ref":"#/components/schemas/WorkflowActionAvailability"},"pause":{"$ref":"#/components/schemas/WorkflowActionAvailability"},"resume":{"$ref":"#/components/schemas/WorkflowActionAvailability"},"rerun":{"$ref":"#/components/schemas/WorkflowActionAvailability"},"edit":{"$ref":"#/components/schemas/WorkflowActionAvailability"},"stop":{"$ref":"#/components/schemas/WorkflowActionAvailability"},"delete":{"$ref":"#/components/schemas/WorkflowActionAvailability"}}},"PresenceRule":{"type":"object","description":"Minimum percentage of rows that must have a value for this field.","required":["target","editedBy","editedAt"],"properties":{"target":{"type":"integer","enum":[0,20,40,60,80,100]},"editedBy":{"type":"string","enum":["default","llm","agent","ops","user"],"description":"Actor type that produced the last edit. API clients send `user`."},"editedByLabel":{"type":"string","description":"Optional human-readable label for the editor (e.g. email for users, agent name for agents)."},"editedAt":{"type":"string","format":"date-time","description":"ISO-8601 timestamp of the last edit."}}},"UniquenessRule":{"type":"object","description":"Minimum percentage of values that must be unique in this column.","required":["target","editedBy","editedAt"],"properties":{"target":{"type":"integer","enum":[0,20,40,60,80,100]},"editedBy":{"type":"string","enum":["default","llm","agent","ops","user"],"description":"Actor type that produced the last edit. API clients send `user`."},"editedByLabel":{"type":"string","description":"Optional human-readable label for the editor (e.g. email for users, agent name for agents)."},"editedAt":{"type":"string","format":"date-time","description":"ISO-8601 timestamp of the last edit."}}},"StringLengthRule":{"type":"object","description":"Bound on the string length in characters.","required":["value","editedBy","editedAt"],"properties":{"value":{"type":"integer","minimum":0},"editedBy":{"type":"string","enum":["default","llm","agent","ops","user"],"description":"Actor type that produced the last edit. API clients send `user`."},"editedByLabel":{"type":"string","description":"Optional human-readable label for the editor (e.g. email for users, agent name for agents)."},"editedAt":{"type":"string","format":"date-time","description":"ISO-8601 timestamp of the last edit."}}},"StringHtmlElementCountRule":{"type":"object","description":"Bound on how many HTML elements the text contains. An element is an opening or\nself-closing tag (e.g. `<h1>Foo</h1> bar` counts 1, `<h1>Foo</h1> <p>bar</p>` counts 2);\nclosing tags, comments, and doctypes don't count.\n","required":["value","editedBy","editedAt"],"properties":{"value":{"type":"integer","minimum":0},"editedBy":{"type":"string","enum":["default","llm","agent","ops","user"],"description":"Actor type that produced the last edit. API clients send `user`."},"editedByLabel":{"type":"string","description":"Optional human-readable label for the editor (e.g. email for users, agent name for agents)."},"editedAt":{"type":"string","format":"date-time","description":"ISO-8601 timestamp of the last edit."}}},"StringCharsetPreset":{"type":"object","description":"A named character-class restriction.","required":["kind","preset"],"properties":{"kind":{"type":"string","enum":["PRESET"]},"preset":{"type":"string","enum":["natural_language","alphanumeric","alpha"]}}},"StringFormatFreeTextRule":{"type":"object","description":"Free-text format. A character-class restriction; length rules apply only with this kind.","required":["kind","charset","editedBy","editedAt"],"properties":{"kind":{"type":"string","enum":["FREE_TEXT"]},"charset":{"$ref":"#/components/schemas/StringCharsetPreset"},"editedBy":{"type":"string","enum":["default","llm","agent","ops","user"],"description":"Actor type that produced the last edit. API clients send `user`."},"editedByLabel":{"type":"string","description":"Optional human-readable label for the editor (e.g. email for users, agent name for agents)."},"editedAt":{"type":"string","format":"date-time","description":"ISO-8601 timestamp of the last edit."}}},"StringPatternPreset":{"type":"object","description":"A named pattern preset.","required":["kind","preset"],"properties":{"kind":{"type":"string","enum":["PRESET"]},"preset":{"type":"string","enum":["url","email","phone","date","datetime","time","uuid","slug"]}}},"StringCustomPattern":{"type":"object","description":"A custom regular expression.","required":["kind","pattern"],"properties":{"kind":{"type":"string","enum":["CUSTOM"]},"pattern":{"type":"string","minLength":1,"description":"Must be a valid regular expression."}}},"StringPatternSource":{"oneOf":[{"$ref":"#/components/schemas/StringPatternPreset"},{"$ref":"#/components/schemas/StringCustomPattern"}],"discriminator":{"propertyName":"kind"}},"StringFormatFormatRule":{"type":"object","description":"Pattern format. Values must match a named pattern preset or a custom regular expression.","required":["kind","source","editedBy","editedAt"],"properties":{"kind":{"type":"string","enum":["FORMAT"]},"source":{"$ref":"#/components/schemas/StringPatternSource"},"editedBy":{"type":"string","enum":["default","llm","agent","ops","user"],"description":"Actor type that produced the last edit. API clients send `user`."},"editedByLabel":{"type":"string","description":"Optional human-readable label for the editor (e.g. email for users, agent name for agents)."},"editedAt":{"type":"string","format":"date-time","description":"ISO-8601 timestamp of the last edit."}}},"StringListPreset":{"type":"object","description":"A named list of allowed values.","required":["kind","preset"],"properties":{"kind":{"type":"string","enum":["PRESET"]},"preset":{"type":"string","enum":["language2","country2","country3","currency3","month3","usState2"]}}},"StringCustomList":{"type":"object","description":"A custom closed set of allowed values.","required":["kind","values"],"properties":{"kind":{"type":"string","enum":["CUSTOM"]},"values":{"type":"array","items":{"type":"string","minLength":1},"minItems":1,"description":"The closed set of allowed values."}}},"StringListSource":{"oneOf":[{"$ref":"#/components/schemas/StringListPreset"},{"$ref":"#/components/schemas/StringCustomList"}],"discriminator":{"propertyName":"kind"}},"StringFormatListRule":{"type":"object","description":"List format. Values must come from a named list preset or a custom list.","required":["kind","source","editedBy","editedAt"],"properties":{"kind":{"type":"string","enum":["LIST"]},"source":{"$ref":"#/components/schemas/StringListSource"},"editedBy":{"type":"string","enum":["default","llm","agent","ops","user"],"description":"Actor type that produced the last edit. API clients send `user`."},"editedByLabel":{"type":"string","description":"Optional human-readable label for the editor (e.g. email for users, agent name for agents)."},"editedAt":{"type":"string","format":"date-time","description":"ISO-8601 timestamp of the last edit."}}},"StringFormatRule":{"description":"Format rule for string fields. The `kind` discriminator selects one of three shapes:\n  - `FREE_TEXT` (see `StringFormatFreeTextRule`): a character-class restriction. Length rules apply only with this kind.\n  - `FORMAT` (see `StringFormatFormatRule`): a named pattern preset or a custom regex.\n  - `LIST` (see `StringFormatListRule`): a named list preset or a custom list of allowed values.\n","oneOf":[{"$ref":"#/components/schemas/StringFormatFreeTextRule"},{"$ref":"#/components/schemas/StringFormatFormatRule"},{"$ref":"#/components/schemas/StringFormatListRule"}],"discriminator":{"propertyName":"kind"}},"NumberBoundRule":{"type":"object","description":"Inclusive bound on the numeric value.","required":["value","editedBy","editedAt"],"properties":{"value":{"type":"number"},"editedBy":{"type":"string","enum":["default","llm","agent","ops","user"],"description":"Actor type that produced the last edit. API clients send `user`."},"editedByLabel":{"type":"string","description":"Optional human-readable label for the editor (e.g. email for users, agent name for agents)."},"editedAt":{"type":"string","format":"date-time","description":"ISO-8601 timestamp of the last edit."}}},"NumberMaxDecimalPlacesRule":{"type":"object","description":"Maximum number of decimal places (0 for whole numbers).","required":["value","editedBy","editedAt"],"properties":{"value":{"type":"integer","minimum":0,"maximum":16},"editedBy":{"type":"string","enum":["default","llm","agent","ops","user"],"description":"Actor type that produced the last edit. API clients send `user`."},"editedByLabel":{"type":"string","description":"Optional human-readable label for the editor (e.g. email for users, agent name for agents)."},"editedAt":{"type":"string","format":"date-time","description":"ISO-8601 timestamp of the last edit."}}},"DateFixedBoundRule":{"type":"object","description":"A fixed calendar date bound.","required":["kind","date","editedBy","editedAt"],"properties":{"kind":{"type":"string","enum":["FIXED"]},"date":{"type":"string","format":"date","description":"A valid calendar date in `YYYY-MM-DD` format."},"editedBy":{"type":"string","enum":["default","llm","agent","ops","user"],"description":"Actor type that produced the last edit. API clients send `user`."},"editedByLabel":{"type":"string","description":"Optional human-readable label for the editor (e.g. email for users, agent name for agents)."},"editedAt":{"type":"string","format":"date-time","description":"ISO-8601 timestamp of the last edit."}}},"DateRelativeBoundRule":{"type":"object","description":"A bound relative to the run date (UTC). As a minimum it resolves to the first day of the\nperiod, as a maximum to the last day (e.g. `THIS_MONTH` is the 1st or the last day of the run month).\n","required":["kind","preset","editedBy","editedAt"],"properties":{"kind":{"type":"string","enum":["RELATIVE"]},"preset":{"type":"string","enum":["TODAY","YESTERDAY","THIS_WEEK","THIS_MONTH","THIS_YEAR"]},"editedBy":{"type":"string","enum":["default","llm","agent","ops","user"],"description":"Actor type that produced the last edit. API clients send `user`."},"editedByLabel":{"type":"string","description":"Optional human-readable label for the editor (e.g. email for users, agent name for agents)."},"editedAt":{"type":"string","format":"date-time","description":"ISO-8601 timestamp of the last edit."}}},"DateBoundRule":{"description":"Inclusive bound on a date value, either fixed or relative to the run date.","oneOf":[{"$ref":"#/components/schemas/DateFixedBoundRule"},{"$ref":"#/components/schemas/DateRelativeBoundRule"}],"discriminator":{"propertyName":"kind"}},"ObjectAdditionalPropertiesRule":{"type":"object","description":"Whether the object may contain properties that are not listed under `properties`.","required":["allowed","editedBy","editedAt"],"properties":{"allowed":{"type":"boolean"},"editedBy":{"type":"string","enum":["default","llm","agent","ops","user"],"description":"Actor type that produced the last edit. API clients send `user`."},"editedByLabel":{"type":"string","description":"Optional human-readable label for the editor (e.g. email for users, agent name for agents)."},"editedAt":{"type":"string","format":"date-time","description":"ISO-8601 timestamp of the last edit."}}},"ArrayItemCountRule":{"type":"object","description":"Bound on the number of items in the array.","required":["value","editedBy","editedAt"],"properties":{"value":{"type":"integer","minimum":0},"editedBy":{"type":"string","enum":["default","llm","agent","ops","user"],"description":"Actor type that produced the last edit. API clients send `user`."},"editedByLabel":{"type":"string","description":"Optional human-readable label for the editor (e.g. email for users, agent name for agents)."},"editedAt":{"type":"string","format":"date-time","description":"ISO-8601 timestamp of the last edit."}}},"StringFieldRules":{"type":"object","required":["kind"],"description":"Validation rules for string fields.","properties":{"kind":{"type":"string","enum":["STRING"]},"presence":{"$ref":"#/components/schemas/PresenceRule"},"uniqueness":{"$ref":"#/components/schemas/UniquenessRule"},"minLength":{"$ref":"#/components/schemas/StringLengthRule"},"maxLength":{"$ref":"#/components/schemas/StringLengthRule"},"minHtmlElements":{"$ref":"#/components/schemas/StringHtmlElementCountRule"},"maxHtmlElements":{"$ref":"#/components/schemas/StringHtmlElementCountRule"},"format":{"$ref":"#/components/schemas/StringFormatRule"}}},"NumberFieldRules":{"type":"object","required":["kind"],"description":"Validation rules for number fields.","properties":{"kind":{"type":"string","enum":["NUMBER"]},"presence":{"$ref":"#/components/schemas/PresenceRule"},"uniqueness":{"$ref":"#/components/schemas/UniquenessRule"},"minimum":{"$ref":"#/components/schemas/NumberBoundRule"},"maximum":{"$ref":"#/components/schemas/NumberBoundRule"},"maxDecimalPlaces":{"$ref":"#/components/schemas/NumberMaxDecimalPlacesRule"}}},"DateFieldRules":{"type":"object","required":["kind"],"description":"Validation rules for date fields. Values are cast to a calendar date (`YYYY-MM-DD`,\nor a `YYYY-MM-DD HH:MM:SS` timestamp truncated to its day) before the bounds apply.\n","properties":{"kind":{"type":"string","enum":["DATE"]},"presence":{"$ref":"#/components/schemas/PresenceRule"},"uniqueness":{"$ref":"#/components/schemas/UniquenessRule"},"minimum":{"$ref":"#/components/schemas/DateBoundRule"},"maximum":{"$ref":"#/components/schemas/DateBoundRule"}}},"ObjectFieldRules":{"type":"object","required":["kind","properties"],"description":"Rules for an object field. `properties` maps each sub-field name to its own rules\n(recursively a `FieldValidationRules`), so nested objects can be validated to any depth.\n","properties":{"kind":{"type":"string","enum":["OBJECT"]},"presence":{"$ref":"#/components/schemas/PresenceRule"},"uniqueness":{"$ref":"#/components/schemas/UniquenessRule"},"additionalProperties":{"$ref":"#/components/schemas/ObjectAdditionalPropertiesRule"},"properties":{"type":"object","description":"Per-sub-field rules, keyed by sub-field name.","additionalProperties":{"$ref":"#/components/schemas/FieldValidationRules"}}}},"ArrayFieldRules":{"type":"object","required":["kind"],"description":"Rules for an array field. `items` are the rules applied to every element of the array\n(recursively a `FieldValidationRules`).\n","properties":{"kind":{"type":"string","enum":["ARRAY"]},"presence":{"$ref":"#/components/schemas/PresenceRule"},"uniqueness":{"$ref":"#/components/schemas/UniquenessRule"},"minItems":{"$ref":"#/components/schemas/ArrayItemCountRule"},"maxItems":{"$ref":"#/components/schemas/ArrayItemCountRule"},"items":{"$ref":"#/components/schemas/FieldValidationRules"}}},"OtherFieldRules":{"type":"object","required":["kind"],"description":"Fallback rules for fields with no richer rule shape (e.g. booleans).","properties":{"kind":{"type":"string","enum":["OTHER"]},"presence":{"$ref":"#/components/schemas/PresenceRule"},"uniqueness":{"$ref":"#/components/schemas/UniquenessRule"}}},"FieldValidationRules":{"description":"Rules for one schema field. The `kind` discriminator selects the rule shape and casts the\nfield's values to that type before evaluation. A rule tree may nest at most 4 levels deep\nand hold at most 200 evaluable rules.\n","oneOf":[{"$ref":"#/components/schemas/StringFieldRules"},{"$ref":"#/components/schemas/NumberFieldRules"},{"$ref":"#/components/schemas/DateFieldRules"},{"$ref":"#/components/schemas/ObjectFieldRules"},{"$ref":"#/components/schemas/ArrayFieldRules"},{"$ref":"#/components/schemas/OtherFieldRules"}],"discriminator":{"propertyName":"kind"}},"WorkflowSchemaValidationRules":{"type":"object","description":"Map keyed by schema field name, with the per-field data quality rules for that field.","additionalProperties":{"$ref":"#/components/schemas/FieldValidationRules"}},"ExtractionStrategySummary":{"type":"object","required":["approach","summary","dataSource"],"properties":{"approach":{"type":"string"},"summary":{"type":"string"},"dataSource":{"type":"object","required":["type","endpoints","interactionStyle","selectors"],"properties":{"type":{"type":"string"},"endpoints":{"type":"array","items":{"type":"string"}},"interactionStyle":{"type":"string"},"selectors":{"type":"array","items":{"type":"string"}}}},"intervalSeconds":{"type":"number","nullable":true,"description":"Realtime polling interval in seconds, when applicable."}}},"AgentPromptRequest":{"type":"object","required":["prompt"],"properties":{"prompt":{"type":"string","minLength":1},"sessionId":{"type":"string","format":"uuid","nullable":true},"newSessionId":{"type":"string","format":"uuid","nullable":true},"threadId":{"type":"string","format":"uuid","nullable":true},"questionsDisabled":{"type":"boolean"},"templateId":{"type":"string","format":"uuid","nullable":true},"templateVersion":{"type":"integer","minimum":1,"nullable":true},"productType":{"type":"string","enum":["workflow","realtime"]},"tags":{"type":"array","items":{"type":"string"}},"notificationChannelIds":{"type":"array","minItems":1,"uniqueItems":true,"items":{"type":"string","format":"uuid"}}}},"AgentPromptResponse":{"type":"object","required":["data","status","message"],"properties":{"data":{"type":"object","required":["jobId","sessionId","threadId","workflowId"],"properties":{"jobId":{"type":"string","nullable":true},"inputEventId":{"type":"string"},"sessionId":{"type":"string","format":"uuid"},"threadId":{"type":"string","format":"uuid"},"workflowId":{"type":"string","format":"uuid"},"existed":{"type":"boolean"}}},"status":{"type":"string","enum":["success"]},"message":{"type":"string"}}},"AssistantQuestion":{"type":"object","additionalProperties":true,"required":["question","header","options","answerType"],"properties":{"question":{"type":"string"},"header":{"type":"string"},"options":{"type":"array","items":{"type":"object","required":["label","description"],"properties":{"label":{"type":"string"},"description":{"type":"string"}}}},"answerType":{"type":"string","enum":["single","multi","freeform"]},"metadata":{"type":"object","additionalProperties":true}}},"WorkflowAssistantMessageRequest":{"type":"object","required":["prompt"],"properties":{"prompt":{"type":"string","minLength":1,"description":"Natural-language instructions for updating the existing workflow."},"threadId":{"type":"string","format":"uuid","nullable":true,"description":"Assistant thread to continue. Omit to use the workflow's latest Assistant thread."}}},"WorkflowAssistantMessageResponse":{"type":"object","required":["data","status","message"],"properties":{"data":{"type":"object","required":["jobId","sessionId","threadId","workflowId"],"properties":{"jobId":{"type":"string","nullable":true},"inputEventId":{"type":"string"},"sessionId":{"type":"string","format":"uuid"},"threadId":{"type":"string","format":"uuid"},"workflowId":{"type":"string","format":"uuid"},"existed":{"type":"boolean"},"alreadyBootstrapped":{"type":"boolean"},"realtimePlacementPolicy":{"type":"object","description":"Present when mentioned tags were saved but the realtime placement policy publish failed or was skipped; the message itself still ran.","properties":{"status":{"type":"string","enum":["failed","skipped"]},"code":{"type":"string","description":"Stable failure code, e.g. REALTIME_PLACEMENT_POLICY_PUBLISH_FAILED."},"reason":{"type":"string"},"policyVersion":{"type":"integer"}}}}},"status":{"type":"string","enum":["success"]},"message":{"type":"string"}}},"AssistantPauseStateResponse":{"type":"object","required":["data","status"],"properties":{"data":{"type":"object","required":["paused","pause","pendingQuestion"],"properties":{"paused":{"type":"boolean"},"pause":{"type":"object","nullable":true,"required":["id","reason","status","pausedAt"],"properties":{"id":{"type":"string"},"reason":{"type":"string","enum":["question","interrupt"]},"status":{"type":"string","enum":["active","resuming"]},"threadId":{"type":"string","format":"uuid"},"pausedAt":{"type":"string","format":"date-time"},"resumeRequestedAt":{"type":"string","format":"date-time"},"resumeError":{"type":"boolean"}}},"pendingQuestion":{"type":"object","nullable":true,"required":["questionId","questions","askedAt"],"properties":{"questionId":{"type":"string"},"threadId":{"type":"string","format":"uuid"},"questions":{"type":"array","items":{"$ref":"#/components/schemas/AssistantQuestion"}},"askedAt":{"type":"string","format":"date-time"}}}}},"status":{"type":"string","enum":["success"]}}},"AssistantAnswerRequest":{"type":"object","required":["sessionId","questionId","answers"],"properties":{"sessionId":{"type":"string","format":"uuid"},"questionId":{"type":"string"},"threadId":{"type":"string","format":"uuid"},"answers":{"type":"object","additionalProperties":{"type":"string"},"description":"Question-index-to-answer map. Freeform answers use the `_freeform` key."}}},"AssistantAnswerResponse":{"type":"object","required":["data","status","message"],"properties":{"data":{"type":"object","required":["success"],"properties":{"success":{"type":"boolean","enum":[true]}}},"status":{"type":"string","enum":["success"]},"message":{"type":"string"}}},"AssistantStrategyResponse":{"type":"object","required":["data","status"],"properties":{"data":{"type":"object","required":["strategy"],"properties":{"strategy":{"allOf":[{"$ref":"#/components/schemas/ExtractionStrategySummary"}],"nullable":true}}},"status":{"type":"string","enum":["success"]}}},"AgentBuild":{"type":"object","required":["id","version","status","createdAt"],"properties":{"id":{"type":"string","format":"uuid"},"version":{"type":"integer"},"status":{"type":"string","enum":["queued","running","completed","failed"]},"errorMessage":{"type":"string","nullable":true},"createdAt":{"type":"string","format":"date-time"},"completedAt":{"type":"string","format":"date-time","nullable":true}}},"AgentBuildsResponse":{"type":"object","required":["data","status"],"properties":{"data":{"type":"object","required":["builds","nextCursor"],"properties":{"builds":{"type":"array","items":{"$ref":"#/components/schemas/AgentBuild"}},"nextCursor":{"type":"string","nullable":true}}},"status":{"type":"string","enum":["success"]}}},"AgentBuildInputResponse":{"type":"object","required":["data","status"],"properties":{"data":{"type":"object","required":["scriptSource","scriptLibVersion"],"properties":{"scriptSource":{"type":"string"},"scriptLibVersion":{"type":"string","nullable":true}}},"status":{"type":"string","enum":["success"]}}},"AssistantControlResponse":{"type":"object","required":["data","status"],"properties":{"data":{"type":"object","required":["success"],"properties":{"success":{"type":"boolean"},"delivery":{"type":"string","enum":["durable","already_paused"]}}},"status":{"type":"string","enum":["success"]}}},"AssistantResumeResponse":{"type":"object","required":["data","status","message"],"properties":{"data":{"type":"object","required":["jobId","sessionId"],"properties":{"jobId":{"type":"string"},"sessionId":{"type":"string","format":"uuid"}}},"status":{"type":"string","enum":["success"]},"message":{"type":"string"}}},"AssistantHistoryUserMessage":{"type":"object","additionalProperties":false,"required":["id","time","kind","role","text"],"properties":{"id":{"type":"string"},"time":{"type":"string","format":"date-time"},"kind":{"type":"string","enum":["user_message"]},"role":{"type":"string","enum":["user"]},"text":{"type":"string"},"authorId":{"type":"string"}}},"AssistantHistoryMessage":{"type":"object","additionalProperties":false,"required":["id","time","kind","role","text"],"properties":{"id":{"type":"string"},"time":{"type":"string","format":"date-time"},"kind":{"type":"string","enum":["assistant_message"]},"role":{"type":"string","enum":["assistant"]},"text":{"type":"string"},"links":{"type":"array","items":{"type":"object","additionalProperties":false,"required":["url"],"properties":{"url":{"type":"string","format":"uri"}}}}}},"AssistantHistoryQuestion":{"type":"object","additionalProperties":false,"required":["id","time","kind","questionId","questions","answers","status"],"properties":{"id":{"type":"string"},"time":{"type":"string","format":"date-time"},"kind":{"type":"string","enum":["question"]},"questionId":{"type":"string"},"questions":{"type":"array","items":{"$ref":"#/components/schemas/AssistantQuestion"}},"answers":{"type":"object","nullable":true,"additionalProperties":true},"status":{"type":"string","enum":["answered","unanswered"]}}},"AssistantHistoryItem":{"oneOf":[{"$ref":"#/components/schemas/AssistantHistoryUserMessage"},{"$ref":"#/components/schemas/AssistantHistoryMessage"},{"$ref":"#/components/schemas/AssistantHistoryQuestion"}],"discriminator":{"propertyName":"kind"}},"AssistantHistoryResponse":{"type":"object","required":["data","status"],"properties":{"data":{"type":"object","required":["workflowId","sessionId","items","pagination"],"properties":{"workflowId":{"type":"string","format":"uuid"},"sessionId":{"type":"string","format":"uuid"},"items":{"type":"array","items":{"$ref":"#/components/schemas/AssistantHistoryItem"}},"pagination":{"type":"object","required":["nextCursor","hasMore"],"properties":{"nextCursor":{"type":"string","nullable":true},"hasMore":{"type":"boolean"}}}}},"status":{"type":"string","enum":["success"]}}},"AgentErrorEnvelope":{"type":"object","description":"Error envelope shared by every v5 agent endpoint. `code` is always present and stable. Conflict codes SESSION_NOT_ACTIVE, SESSION_ALREADY_ACTIVE and PAUSE_ANSWER_CONFLICT are terminal successes — the desired state already holds, do not retry-loop. `outcome: \"unknown\"` (with an *_OUTCOME_UNKNOWN code) marks an indeterminate dispatch: the work may already have started; re-send only when `retrySafe` is true, or with your original idempotencyKey. `retryAfterMs` accompanies retryable 503 responses.","required":["data","status","code","message"],"properties":{"data":{"nullable":true},"status":{"type":"string","enum":["error"]},"code":{"type":"string"},"message":{"type":"string"},"outcome":{"type":"string","enum":["unknown"]},"retrySafe":{"type":"boolean"},"retryAfterMs":{"type":"number"},"residue":{"type":"object","description":"Identifiers of state left behind when compensation failed; keep them for support.","additionalProperties":{"type":"string"}}}},"EmailChannelConfig":{"type":"object","required":["recipients"],"properties":{"recipients":{"type":"array","items":{"type":"string","format":"email"},"description":"Array of recipient email addresses","example":["user@example.com","admin@company.com"]},"from":{"type":"string","format":"email","description":"Sender email address (optional, must be a @kadoa.com domain email)","example":"notifications@kadoa.com"}}},"SlackChannelConfig":{"type":"object","required":["slackChannelId","slackChannelName"],"properties":{"webhookUrl":{"type":"string","format":"uri","description":"Slack webhook URL (optional)","example":"https://example.com/slack-webhook"},"slackChannelId":{"type":"string","description":"Slack channel ID","example":"C1234567890"},"slackChannelName":{"type":"string","description":"Slack channel name","example":"general"}}},"WebhookChannelConfig":{"type":"object","required":["webhookUrl","httpMethod"],"properties":{"webhookUrl":{"type":"string","format":"uri","description":"Webhook endpoint URL","example":"https://api.example.com/webhook"},"httpMethod":{"type":"string","enum":["POST","GET","PUT","PATCH"],"description":"HTTP method for the webhook"},"auth":{"type":"object","description":"Authentication configuration (optional)","properties":{"type":{"type":"string","enum":["bearer","basic","header"],"description":"Authentication type"},"token":{"type":"string","description":"Bearer token (for bearer auth)"},"username":{"type":"string","description":"Username (for basic auth)"},"password":{"type":"string","description":"Password (for basic auth)"},"headers":{"type":"object","description":"Additional headers (for header auth)","additionalProperties":{"type":"string"}}}}}},"WebsocketChannelConfig":{"type":"object","description":"WebSocket channel configuration. Note - Only one WebSocket channel is allowed per workspace. Leave empty object {} as no configuration is needed.","properties":{}},"CreateCrawlerConfigRequest":{"type":"object","properties":{"url":{"type":"string","format":"uri","description":"Single URL to start crawling (for backward compatibility)"},"startUrls":{"type":"array","items":{"type":"string","format":"uri","minLength":1},"description":"List of URLs for crawling"},"pathsFilterIn":{"type":"array","items":{"type":"string","minLength":1},"description":"Regex patterns to include specific full URLs. Accepts array or JSON-stringified array of regex source strings."},"pathsFilterOut":{"type":"array","items":{"type":"string","minLength":1},"description":"Regex patterns to exclude specific full URLs. Accepts array or JSON-stringified array of regex source strings."},"proxyType":{"type":"string","nullable":true,"description":"Type of proxy to use"},"proxyCountry":{"type":"string","nullable":true,"description":"Country for proxy selection"},"timeout":{"type":"number","minimum":1,"description":"Timeout in milliseconds"},"maxDepth":{"type":"number","minimum":1,"description":"Maximum crawling depth"},"maxPages":{"type":"number","minimum":1,"description":"Maximum number of pages to crawl"},"maxMatches":{"type":"number","minimum":1,"description":"Maximum number of matched pages to crawl before stopping"},"concurrency":{"type":"number","minimum":1,"description":"Number of concurrent crawlers"},"strictDomain":{"default":true,"type":"boolean","description":"Whether to stay within the same domain"},"loadImages":{"default":true,"type":"boolean","description":"Whether to load images during crawling"},"safeMode":{"default":false,"type":"boolean","description":"Enable safe mode for crawling"},"callbackUrl":{"type":"string","format":"uri","nullable":true,"description":"Webhook URL for completion notifications"},"processDuringCrawl":{"type":"boolean","description":"Whether to run preprocessing and extraction during the crawl phase"},"crawlMethod":{"type":"object","properties":{"mode":{"default":"auto","type":"string","enum":["auto","browser"],"description":"Worker selection mode. 'auto' (default) picks cheapest compatible worker, 'browser' forces browser."},"worker":{"type":"string","enum":["auto","kurl","curl-cffi","kadmium","patchright","camoufox","cloakbrowser","brightdata"],"description":"Crawler engine selection. Fetches use Kurl; browser mode and actions use Kadmium. curl-cffi maps to Kurl; patchright, camoufox, and cloakbrowser map to Kadmium. BrightData is blocked."},"proxy":{"type":"string","enum":["auto","direct","dc","resi","isp"],"description":"Explicit proxy routing override for crawler scraping"}},"additionalProperties":{"nullable":true},"description":"Crawl method configuration"},"matchThreshold":{"type":"number","minimum":0,"maximum":1,"description":"Match threshold override for blueprint filtering"},"blueprint":{"type":"array","items":{"type":"object","properties":{"name":{"type":"string"},"description":{"type":"string"},"selector":{"type":"string"},"type":{"type":"string"}},"additionalProperties":{"nullable":true},"description":"Blueprint field definition"},"description":"Blueprint fields applied during crawling"},"extractionOptions":{"type":"object","properties":{"extractions":{"type":"object","additionalProperties":{"type":"boolean"},"description":"Feature toggles for available extraction helpers"},"schema":{"nullable":true,"description":"Schema definition for structured extractions"},"entity":{"nullable":true,"description":"Entity metadata used for extraction mappings"},"mainContextSelector":{"type":"string","description":"CSS selector anchoring focus-driven extractors"},"xhrExtractorConfigs":{"type":"array","items":{"nullable":true},"description":"XHR extractor configuration entries"}},"additionalProperties":false,"description":"Extraction-related options derived from legacy launch summary"},"navigationOptions":{"type":"object","properties":{"browserActions":{"type":"array","items":{"type":"object","additionalProperties":{"nullable":true}},"description":"Ordered list of scripted browser actions executed after navigation"},"preBrowserActions":{"type":"array","items":{"type":"object","additionalProperties":{"nullable":true}},"description":"Browser actions performed before the main action chain"},"scrollHtml":{"type":"boolean","description":"Enable HTML capture while scrolling through the page"},"scrollHtmlTimeout":{"type":"number","minimum":0,"description":"Maximum scroll duration in milliseconds"},"visualHtml":{"type":"boolean","description":"Enable visual HTML capture for navigation heuristics"},"navigationStrategy":{"type":"string","description":"Primary navigation strategy identifier"},"navigationStrategies":{"type":"array","items":{"type":"string"},"description":"Fallback navigation strategy order"},"limit":{"type":"number","minimum":0,"description":"Maximum number of navigation steps"},"disableNavigation":{"type":"boolean","description":"Skip automated navigation heuristics"},"ignoreIframes":{"type":"boolean","description":"Disable iframe traversal during navigation"},"navigationExploration":{"type":"object","additionalProperties":{"nullable":true},"description":"Navigation exploration tuning payload"},"loadHtmlOnly":{"type":"boolean","description":"Skip scripted interactions and only capture HTML"},"acceptCookies":{"type":"boolean","description":"Force cookie acceptance automation"},"cachedCookieAccept":{"oneOf":[{"type":"boolean"},{"type":"string"}],"description":"Reuse cached cookie acceptance flow"}},"additionalProperties":false,"description":"Navigation-related options derived from legacy launch summary"},"artifactOptions":{"type":"object","properties":{"screenshot":{"type":"boolean","description":"Capture standard screenshot"},"screenshotFull":{"type":"boolean","description":"Capture full-page screenshot"},"screenshotCache":{"type":"boolean","description":"Re-use cached screenshot when available"},"screenshotPublic":{"type":"boolean","description":"Make captured screenshot publicly accessible"},"screenshotLink":{"type":"string","description":"Stored screenshot link for follow-up processing"},"archivePdf":{"type":"boolean","description":"Generate archival PDF for crawled pages"}},"additionalProperties":false,"description":"Artifact capture options derived from legacy launch summary"},"rawMode":{"type":"boolean","description":"Whether this is a raw data mode crawl"},"outputOptions":{"type":"object","properties":{"includeHtml":{"type":"boolean"},"includeMarkdown":{"type":"boolean"},"includeScreenshots":{"type":"boolean"},"includeJson":{"type":"boolean"}},"description":"Output options for raw mode"},"jobId":{"type":"string","description":"Internal: Job ID for workflow tracking"},"workflowId":{"type":"string","description":"Internal: Owning workflow (scraperId) for BrightData cost attribution"},"dataKey":{"type":"string","description":"Internal: Data key for Parquet storage path"},"billingSource":{"type":"string","description":"Internal: Billing source identifier"}},"title":"CreateCrawlerConfigRequest","description":"Request body for creating a new crawling configuration"},"CreateCrawlerConfigResponse":{"type":"object","properties":{"url":{"type":"string","format":"uri","description":"Single URL to start crawling (for backward compatibility)"},"startUrls":{"type":"array","items":{"type":"string","format":"uri","minLength":1},"description":"List of URLs for crawling"},"pathsFilterIn":{"type":"array","items":{"type":"string","minLength":1},"description":"Regex patterns to include specific full URLs. Accepts array or JSON-stringified array of regex source strings."},"pathsFilterOut":{"type":"array","items":{"type":"string","minLength":1},"description":"Regex patterns to exclude specific full URLs. Accepts array or JSON-stringified array of regex source strings."},"proxyType":{"type":"string","nullable":true,"description":"Type of proxy to use"},"proxyCountry":{"type":"string","nullable":true,"description":"Country for proxy selection"},"timeout":{"type":"number","minimum":1,"description":"Timeout in milliseconds"},"maxDepth":{"type":"number","minimum":1,"description":"Maximum crawling depth"},"maxPages":{"type":"number","minimum":1,"description":"Maximum number of pages to crawl"},"maxMatches":{"type":"number","minimum":1,"description":"Maximum number of matched pages to crawl before stopping"},"concurrency":{"type":"number","minimum":1,"description":"Number of concurrent crawlers"},"strictDomain":{"default":true,"type":"boolean","description":"Whether to stay within the same domain"},"loadImages":{"default":true,"type":"boolean","description":"Whether to load images during crawling"},"safeMode":{"default":false,"type":"boolean","description":"Enable safe mode for crawling"},"callbackUrl":{"type":"string","format":"uri","nullable":true,"description":"Webhook URL for completion notifications"},"processDuringCrawl":{"type":"boolean","description":"Whether to run preprocessing and extraction during the crawl phase"},"crawlMethod":{"type":"object","properties":{"mode":{"default":"auto","type":"string","enum":["auto","browser"],"description":"Worker selection mode. 'auto' (default) picks cheapest compatible worker, 'browser' forces browser."},"worker":{"type":"string","enum":["auto","kurl","curl-cffi","kadmium","patchright","camoufox","cloakbrowser","brightdata"],"description":"Crawler engine selection. Fetches use Kurl; browser mode and actions use Kadmium. curl-cffi maps to Kurl; patchright, camoufox, and cloakbrowser map to Kadmium. BrightData is blocked."},"proxy":{"type":"string","enum":["auto","direct","dc","resi","isp"],"description":"Explicit proxy routing override for crawler scraping"}},"additionalProperties":{"nullable":true},"description":"Crawl method configuration"},"matchThreshold":{"type":"number","minimum":0,"maximum":1,"description":"Match threshold override for blueprint filtering"},"blueprint":{"type":"array","items":{"type":"object","properties":{"name":{"type":"string"},"description":{"type":"string"},"selector":{"type":"string"},"type":{"type":"string"}},"additionalProperties":{"nullable":true},"description":"Blueprint field definition"},"description":"Blueprint fields applied during crawling"},"extractionOptions":{"type":"object","properties":{"extractions":{"type":"object","additionalProperties":{"type":"boolean"},"description":"Feature toggles for available extraction helpers"},"schema":{"nullable":true,"description":"Schema definition for structured extractions"},"entity":{"nullable":true,"description":"Entity metadata used for extraction mappings"},"mainContextSelector":{"type":"string","description":"CSS selector anchoring focus-driven extractors"},"xhrExtractorConfigs":{"type":"array","items":{"nullable":true},"description":"XHR extractor configuration entries"}},"additionalProperties":false,"description":"Extraction-related options derived from legacy launch summary"},"navigationOptions":{"type":"object","properties":{"browserActions":{"type":"array","items":{"type":"object","additionalProperties":{"nullable":true}},"description":"Ordered list of scripted browser actions executed after navigation"},"preBrowserActions":{"type":"array","items":{"type":"object","additionalProperties":{"nullable":true}},"description":"Browser actions performed before the main action chain"},"scrollHtml":{"type":"boolean","description":"Enable HTML capture while scrolling through the page"},"scrollHtmlTimeout":{"type":"number","minimum":0,"description":"Maximum scroll duration in milliseconds"},"visualHtml":{"type":"boolean","description":"Enable visual HTML capture for navigation heuristics"},"navigationStrategy":{"type":"string","description":"Primary navigation strategy identifier"},"navigationStrategies":{"type":"array","items":{"type":"string"},"description":"Fallback navigation strategy order"},"limit":{"type":"number","minimum":0,"description":"Maximum number of navigation steps"},"disableNavigation":{"type":"boolean","description":"Skip automated navigation heuristics"},"ignoreIframes":{"type":"boolean","description":"Disable iframe traversal during navigation"},"navigationExploration":{"type":"object","additionalProperties":{"nullable":true},"description":"Navigation exploration tuning payload"},"loadHtmlOnly":{"type":"boolean","description":"Skip scripted interactions and only capture HTML"},"acceptCookies":{"type":"boolean","description":"Force cookie acceptance automation"},"cachedCookieAccept":{"oneOf":[{"type":"boolean"},{"type":"string"}],"description":"Reuse cached cookie acceptance flow"}},"additionalProperties":false,"description":"Navigation-related options derived from legacy launch summary"},"artifactOptions":{"type":"object","properties":{"screenshot":{"type":"boolean","description":"Capture standard screenshot"},"screenshotFull":{"type":"boolean","description":"Capture full-page screenshot"},"screenshotCache":{"type":"boolean","description":"Re-use cached screenshot when available"},"screenshotPublic":{"type":"boolean","description":"Make captured screenshot publicly accessible"},"screenshotLink":{"type":"string","description":"Stored screenshot link for follow-up processing"},"archivePdf":{"type":"boolean","description":"Generate archival PDF for crawled pages"}},"additionalProperties":false,"description":"Artifact capture options derived from legacy launch summary"},"rawMode":{"type":"boolean","description":"Whether this is a raw data mode crawl"},"outputOptions":{"type":"object","properties":{"includeHtml":{"type":"boolean"},"includeMarkdown":{"type":"boolean"},"includeScreenshots":{"type":"boolean"},"includeJson":{"type":"boolean"}},"description":"Output options for raw mode"},"jobId":{"type":"string","description":"Internal: Job ID for workflow tracking"},"workflowId":{"type":"string","description":"Internal: Owning workflow (scraperId) for BrightData cost attribution"},"dataKey":{"type":"string","description":"Internal: Data key for Parquet storage path"},"billingSource":{"type":"string","description":"Internal: Billing source identifier"},"configId":{"type":"string","description":"Config ID"},"userId":{"type":"string","description":"User ID"},"createdAt":{"type":"string","description":"Created at"}},"required":["configId","userId","createdAt"],"title":"CreateCrawlerConfigResponse","description":"Response schema for creating a new crawling configuration"},"GetCrawlerConfigResponse":{"type":"object","properties":{"url":{"type":"string","format":"uri","description":"Single URL to start crawling (for backward compatibility)"},"startUrls":{"type":"array","items":{"type":"string","format":"uri","minLength":1},"description":"List of URLs for crawling"},"pathsFilterIn":{"type":"array","items":{"type":"string","minLength":1},"description":"Regex patterns to include specific full URLs. Accepts array or JSON-stringified array of regex source strings."},"pathsFilterOut":{"type":"array","items":{"type":"string","minLength":1},"description":"Regex patterns to exclude specific full URLs. Accepts array or JSON-stringified array of regex source strings."},"proxyType":{"type":"string","nullable":true,"description":"Type of proxy to use"},"proxyCountry":{"type":"string","nullable":true,"description":"Country for proxy selection"},"timeout":{"type":"number","minimum":1,"description":"Timeout in milliseconds"},"maxDepth":{"type":"number","minimum":1,"description":"Maximum crawling depth"},"maxPages":{"type":"number","minimum":1,"description":"Maximum number of pages to crawl"},"maxMatches":{"type":"number","minimum":1,"description":"Maximum number of matched pages to crawl before stopping"},"concurrency":{"type":"number","minimum":1,"description":"Number of concurrent crawlers"},"strictDomain":{"default":true,"type":"boolean","description":"Whether to stay within the same domain"},"loadImages":{"default":true,"type":"boolean","description":"Whether to load images during crawling"},"safeMode":{"default":false,"type":"boolean","description":"Enable safe mode for crawling"},"callbackUrl":{"type":"string","format":"uri","nullable":true,"description":"Webhook URL for completion notifications"},"processDuringCrawl":{"type":"boolean","description":"Whether to run preprocessing and extraction during the crawl phase"},"crawlMethod":{"type":"object","properties":{"mode":{"default":"auto","type":"string","enum":["auto","browser"],"description":"Worker selection mode. 'auto' (default) picks cheapest compatible worker, 'browser' forces browser."},"worker":{"type":"string","enum":["auto","kurl","curl-cffi","kadmium","patchright","camoufox","cloakbrowser","brightdata"],"description":"Crawler engine selection. Fetches use Kurl; browser mode and actions use Kadmium. curl-cffi maps to Kurl; patchright, camoufox, and cloakbrowser map to Kadmium. BrightData is blocked."},"proxy":{"type":"string","enum":["auto","direct","dc","resi","isp"],"description":"Explicit proxy routing override for crawler scraping"}},"additionalProperties":{"nullable":true},"description":"Crawl method configuration"},"matchThreshold":{"type":"number","minimum":0,"maximum":1,"description":"Match threshold override for blueprint filtering"},"blueprint":{"type":"array","items":{"type":"object","properties":{"name":{"type":"string"},"description":{"type":"string"},"selector":{"type":"string"},"type":{"type":"string"}},"additionalProperties":{"nullable":true},"description":"Blueprint field definition"},"description":"Blueprint fields applied during crawling"},"extractionOptions":{"type":"object","properties":{"extractions":{"type":"object","additionalProperties":{"type":"boolean"},"description":"Feature toggles for available extraction helpers"},"schema":{"nullable":true,"description":"Schema definition for structured extractions"},"entity":{"nullable":true,"description":"Entity metadata used for extraction mappings"},"mainContextSelector":{"type":"string","description":"CSS selector anchoring focus-driven extractors"},"xhrExtractorConfigs":{"type":"array","items":{"nullable":true},"description":"XHR extractor configuration entries"}},"additionalProperties":false,"description":"Extraction-related options derived from legacy launch summary"},"navigationOptions":{"type":"object","properties":{"browserActions":{"type":"array","items":{"type":"object","additionalProperties":{"nullable":true}},"description":"Ordered list of scripted browser actions executed after navigation"},"preBrowserActions":{"type":"array","items":{"type":"object","additionalProperties":{"nullable":true}},"description":"Browser actions performed before the main action chain"},"scrollHtml":{"type":"boolean","description":"Enable HTML capture while scrolling through the page"},"scrollHtmlTimeout":{"type":"number","minimum":0,"description":"Maximum scroll duration in milliseconds"},"visualHtml":{"type":"boolean","description":"Enable visual HTML capture for navigation heuristics"},"navigationStrategy":{"type":"string","description":"Primary navigation strategy identifier"},"navigationStrategies":{"type":"array","items":{"type":"string"},"description":"Fallback navigation strategy order"},"limit":{"type":"number","minimum":0,"description":"Maximum number of navigation steps"},"disableNavigation":{"type":"boolean","description":"Skip automated navigation heuristics"},"ignoreIframes":{"type":"boolean","description":"Disable iframe traversal during navigation"},"navigationExploration":{"type":"object","additionalProperties":{"nullable":true},"description":"Navigation exploration tuning payload"},"loadHtmlOnly":{"type":"boolean","description":"Skip scripted interactions and only capture HTML"},"acceptCookies":{"type":"boolean","description":"Force cookie acceptance automation"},"cachedCookieAccept":{"oneOf":[{"type":"boolean"},{"type":"string"}],"description":"Reuse cached cookie acceptance flow"}},"additionalProperties":false,"description":"Navigation-related options derived from legacy launch summary"},"artifactOptions":{"type":"object","properties":{"screenshot":{"type":"boolean","description":"Capture standard screenshot"},"screenshotFull":{"type":"boolean","description":"Capture full-page screenshot"},"screenshotCache":{"type":"boolean","description":"Re-use cached screenshot when available"},"screenshotPublic":{"type":"boolean","description":"Make captured screenshot publicly accessible"},"screenshotLink":{"type":"string","description":"Stored screenshot link for follow-up processing"},"archivePdf":{"type":"boolean","description":"Generate archival PDF for crawled pages"}},"additionalProperties":false,"description":"Artifact capture options derived from legacy launch summary"},"rawMode":{"type":"boolean","description":"Whether this is a raw data mode crawl"},"outputOptions":{"type":"object","properties":{"includeHtml":{"type":"boolean"},"includeMarkdown":{"type":"boolean"},"includeScreenshots":{"type":"boolean"},"includeJson":{"type":"boolean"}},"description":"Output options for raw mode"},"jobId":{"type":"string","description":"Internal: Job ID for workflow tracking"},"workflowId":{"type":"string","description":"Internal: Owning workflow (scraperId) for BrightData cost attribution"},"dataKey":{"type":"string","description":"Internal: Data key for Parquet storage path"},"billingSource":{"type":"string","description":"Internal: Billing source identifier"},"configId":{"type":"string","description":"Config ID"},"userId":{"type":"string","description":"User ID"},"createdAt":{"type":"string","description":"Created at"}},"required":["configId","userId","createdAt"],"title":"GetCrawlerConfigResponse","description":"Response schema for getting a crawling configuration"},"DeleteCrawlerConfigRequest":{"type":"object","properties":{"configId":{"type":"string","description":"Config ID"}},"required":["configId"],"title":"DeleteCrawlerConfigRequest","description":"Schema for deleting a crawling configuration"},"DeleteCrawlerConfigResponse":{"type":"object","properties":{"configId":{"type":"string","description":"Config ID"},"deleted":{"type":"boolean","description":"Whether the config was deleted"}},"required":["configId","deleted"],"title":"DeleteCrawlerConfigResponse","description":"Response schema for deleting a crawling configuration"},"StartCrawlerSessionRequest":{"type":"object","properties":{"url":{"type":"string","format":"uri","description":"Single URL to start crawling (for backward compatibility)"},"startUrls":{"type":"array","items":{"type":"string","format":"uri","minLength":1},"description":"List of URLs for crawling"},"pathsFilterIn":{"type":"array","items":{"type":"string","minLength":1},"description":"Regex patterns to include specific full URLs. Accepts array or JSON-stringified array of regex source strings."},"pathsFilterOut":{"type":"array","items":{"type":"string","minLength":1},"description":"Regex patterns to exclude specific full URLs. Accepts array or JSON-stringified array of regex source strings."},"proxyType":{"type":"string","nullable":true,"description":"Type of proxy to use"},"proxyCountry":{"type":"string","nullable":true,"description":"Country for proxy selection"},"timeout":{"type":"number","minimum":1,"description":"Timeout in milliseconds"},"maxDepth":{"type":"number","minimum":1,"description":"Maximum crawling depth"},"maxPages":{"type":"number","minimum":1,"description":"Maximum number of pages to crawl"},"maxMatches":{"type":"number","minimum":1,"description":"Maximum number of matched pages to crawl before stopping"},"concurrency":{"type":"number","minimum":1,"description":"Number of concurrent crawlers"},"strictDomain":{"default":true,"type":"boolean","description":"Whether to stay within the same domain"},"loadImages":{"default":true,"type":"boolean","description":"Whether to load images during crawling"},"safeMode":{"default":false,"type":"boolean","description":"Enable safe mode for crawling"},"callbackUrl":{"type":"string","format":"uri","nullable":true,"description":"Webhook URL for completion notifications"},"processDuringCrawl":{"type":"boolean","description":"Whether to run preprocessing and extraction during the crawl phase"},"crawlMethod":{"type":"object","properties":{"mode":{"default":"auto","type":"string","enum":["auto","browser"],"description":"Worker selection mode. 'auto' (default) picks cheapest compatible worker, 'browser' forces browser."},"worker":{"type":"string","enum":["auto","kurl","curl-cffi","kadmium","patchright","camoufox","cloakbrowser","brightdata"],"description":"Crawler engine selection. Fetches use Kurl; browser mode and actions use Kadmium. curl-cffi maps to Kurl; patchright, camoufox, and cloakbrowser map to Kadmium. BrightData is blocked."},"proxy":{"type":"string","enum":["auto","direct","dc","resi","isp"],"description":"Explicit proxy routing override for crawler scraping"}},"additionalProperties":{"nullable":true},"description":"Crawl method configuration"},"matchThreshold":{"type":"number","minimum":0,"maximum":1,"description":"Match threshold override for blueprint filtering"},"blueprint":{"type":"array","items":{"type":"object","properties":{"name":{"type":"string"},"description":{"type":"string"},"selector":{"type":"string"},"type":{"type":"string"}},"additionalProperties":{"nullable":true},"description":"Blueprint field definition"},"description":"Blueprint fields applied during crawling"},"extractionOptions":{"type":"object","properties":{"extractions":{"type":"object","additionalProperties":{"type":"boolean"},"description":"Feature toggles for available extraction helpers"},"schema":{"nullable":true,"description":"Schema definition for structured extractions"},"entity":{"nullable":true,"description":"Entity metadata used for extraction mappings"},"mainContextSelector":{"type":"string","description":"CSS selector anchoring focus-driven extractors"},"xhrExtractorConfigs":{"type":"array","items":{"nullable":true},"description":"XHR extractor configuration entries"}},"additionalProperties":false,"description":"Extraction-related options derived from legacy launch summary"},"navigationOptions":{"type":"object","properties":{"browserActions":{"type":"array","items":{"type":"object","additionalProperties":{"nullable":true}},"description":"Ordered list of scripted browser actions executed after navigation"},"preBrowserActions":{"type":"array","items":{"type":"object","additionalProperties":{"nullable":true}},"description":"Browser actions performed before the main action chain"},"scrollHtml":{"type":"boolean","description":"Enable HTML capture while scrolling through the page"},"scrollHtmlTimeout":{"type":"number","minimum":0,"description":"Maximum scroll duration in milliseconds"},"visualHtml":{"type":"boolean","description":"Enable visual HTML capture for navigation heuristics"},"navigationStrategy":{"type":"string","description":"Primary navigation strategy identifier"},"navigationStrategies":{"type":"array","items":{"type":"string"},"description":"Fallback navigation strategy order"},"limit":{"type":"number","minimum":0,"description":"Maximum number of navigation steps"},"disableNavigation":{"type":"boolean","description":"Skip automated navigation heuristics"},"ignoreIframes":{"type":"boolean","description":"Disable iframe traversal during navigation"},"navigationExploration":{"type":"object","additionalProperties":{"nullable":true},"description":"Navigation exploration tuning payload"},"loadHtmlOnly":{"type":"boolean","description":"Skip scripted interactions and only capture HTML"},"acceptCookies":{"type":"boolean","description":"Force cookie acceptance automation"},"cachedCookieAccept":{"oneOf":[{"type":"boolean"},{"type":"string"}],"description":"Reuse cached cookie acceptance flow"}},"additionalProperties":false,"description":"Navigation-related options derived from legacy launch summary"},"artifactOptions":{"type":"object","properties":{"screenshot":{"type":"boolean","description":"Capture standard screenshot"},"screenshotFull":{"type":"boolean","description":"Capture full-page screenshot"},"screenshotCache":{"type":"boolean","description":"Re-use cached screenshot when available"},"screenshotPublic":{"type":"boolean","description":"Make captured screenshot publicly accessible"},"screenshotLink":{"type":"string","description":"Stored screenshot link for follow-up processing"},"archivePdf":{"type":"boolean","description":"Generate archival PDF for crawled pages"}},"additionalProperties":false,"description":"Artifact capture options derived from legacy launch summary"},"rawMode":{"type":"boolean","description":"Whether this is a raw data mode crawl"},"outputOptions":{"type":"object","properties":{"includeHtml":{"type":"boolean"},"includeMarkdown":{"type":"boolean"},"includeScreenshots":{"type":"boolean"},"includeJson":{"type":"boolean"}},"description":"Output options for raw mode"},"jobId":{"type":"string","description":"Internal: Job ID for workflow tracking"},"workflowId":{"type":"string","description":"Internal: Owning workflow (scraperId) for BrightData cost attribution"},"dataKey":{"type":"string","description":"Internal: Data key for Parquet storage path"},"billingSource":{"type":"string","description":"Internal: Billing source identifier"}},"title":"StartCrawlerSessionRequest","description":"Schema for starting a crawling session with support for both single URL and multiple URLs"},"StartCrawlerSessionResponse":{"type":"object","properties":{"message":{"type":"string","description":"Response message"},"sessionId":{"type":"string","description":"Session ID"},"configId":{"type":"string","description":"Config ID (included when creating config and starting session)"},"error":{"type":"string","description":"Error message if any","nullable":true}},"required":["message","sessionId","error"],"title":"StartCrawlerSessionResponse","description":"Response schema for starting a crawling session"},"StartSessionWithConfigRequest":{"type":"object","properties":{"configId":{"type":"string","description":"Configuration ID to use for this session"}},"required":["configId"],"title":"StartSessionWithConfigRequest","description":"Schema for starting a session with an existing configuration"},"PauseCrawlerSessionRequest":{"type":"object","properties":{"sessionId":{"type":"string","description":"Session ID"}},"required":["sessionId"],"title":"PauseCrawlerSessionRequest","description":"Schema for pausing a crawling session"},"PauseCrawlerSessionResponse":{"type":"object","properties":{"message":{"type":"string","description":"Response message"},"sessionId":{"type":"string","description":"Session ID"},"error":{"type":"string","description":"Error message if any","nullable":true}},"required":["message","sessionId","error"],"title":"PauseCrawlerSessionResponse","description":"Response schema for pausing a crawling session"},"ResumeCrawlerSessionRequest":{"type":"object","properties":{"sessionId":{"type":"string","description":"Session ID"}},"required":["sessionId"],"title":"ResumeCrawlerSessionRequest","description":"Schema for resuming a crawling session"},"ResumeCrawlerSessionResponse":{"type":"object","properties":{"message":{"type":"string","description":"Response message"},"sessionId":{"type":"string","description":"Session ID"},"error":{"type":"string","description":"Error message if any","nullable":true}},"required":["message","sessionId","error"],"title":"ResumeCrawlerSessionResponse","description":"Response schema for resuming a crawling session"},"GetCrawlerSessionStatusResponse":{"type":"object","properties":{"payload":{"description":"Details about the crawling session status","nullable":true},"sessionId":{"type":"string","description":"Session ID"},"error":{"type":"string","description":"Error message if any","nullable":true}},"required":["sessionId","error"],"title":"GetCrawlerSessionStatusResponse","description":"Response schema for getting a crawling session status"},"GetCrawlerSessionPagesResponse":{"type":"object","properties":{"payload":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string","description":"Unique ID of the crawled page"},"url":{"type":"string","description":"URL of the crawled page"},"status":{"type":"string","enum":["DONE","CRAWLING","PENDING"],"description":"Status of the page crawl"}},"required":["id","url","status"]},"description":"List of crawled pages with statuses"},"pagination":{"type":"object","properties":{"page":{"type":"number","description":"Current page number"},"pageSize":{"type":"number","description":"Items per page"},"totalItems":{"type":"number","description":"Total number of items"},"totalPages":{"type":"number","description":"Total number of pages"},"hasMore":{"type":"boolean","description":"Whether there are more pages"}},"required":["page","pageSize","totalItems","totalPages","hasMore"],"description":"Pagination details"},"sessionId":{"type":"string","description":"ID of the crawling session"},"error":{"type":"string","description":"Error message if any","nullable":true}},"required":["payload","pagination","sessionId","error"],"title":"GetCrawlerSessionPagesResponse","description":"Response schema for getting paginated session pages"},"GetCrawlerSessionPageResponse":{"type":"object","properties":{"payload":{"description":"Data associated with the specific page","nullable":true},"pageId":{"type":"string","description":"Unique ID of the page"},"pageFormat":{"type":"string","description":"Format of the retrieved page data"},"sessionId":{"type":"string","description":"Session ID"},"error":{"type":"string","description":"Error message if any","nullable":true}},"required":["pageId","pageFormat","sessionId","error"],"title":"GetCrawlerSessionPageResponse","description":"Response schema for getting a specific session page content"},"GetCrawlerBucketDataResponse":{"title":"GetCrawlerBucketDataResponse","description":"Response schema for getting a crawling bucket data - returns file stream for HTML/images"},"GetCrawlerSessionDataListResponse":{"type":"object","properties":{"totalPages":{"type":"number","description":"Total number of pages in the session"},"data":{"type":"array","items":{"type":"object","properties":{"url":{"type":"string","description":"URL of the page"},"status":{"type":"string","description":"Status of the page"},"created_at":{"type":"string","description":"Timestamp when the entry was created"},"html_filename":{"type":"string","description":"Base64 encoded filename for the HTML content (null when HTML not stored)","nullable":true},"screenshot_filename":{"type":"string","description":"Base64 encoded filename for the screenshot (null when screenshot not available)","nullable":true},"processed_html_filename":{"type":"string","description":"Base64 encoded filename for the processed Kadoa HTML","nullable":true},"json_filename":{"type":"string","description":"Base64 encoded filename for the crawler result JSON","nullable":true},"match_score":{"type":"number","description":"Match score between 0 and 1 (null when blueprint not provided)","nullable":true},"matched_fields":{"type":"number","description":"Number of blueprint fields populated for the page","nullable":true},"total_fields":{"type":"number","description":"Total blueprint fields evaluated for matching","nullable":true},"is_match":{"type":"boolean","description":"Whether the page met the blueprint match threshold"}},"required":["url","status","created_at","html_filename","screenshot_filename","processed_html_filename","json_filename","match_score","matched_fields","total_fields","is_match"]},"description":"List of pages in the session"}},"required":["totalPages","data"],"title":"GetCrawlerSessionDataListResponse","description":"Response schema for getting a crawling session data list"},"CrawlerSessionItem":{"type":"object","properties":{"sessionId":{"type":"string","description":"Session ID"},"configId":{"type":"string","description":"Config ID"},"domain":{"type":"string","description":"Domain being crawled"},"startUrls":{"type":"array","items":{"type":"string"},"description":"URLs used to start the crawl"},"userId":{"type":"string","description":"User ID who created the session"},"createdAt":{"type":"string","description":"Session creation timestamp"},"activeJobs":{"type":"number","description":"Number of active jobs (live stat)"},"waitingJobs":{"type":"number","description":"Number of waiting jobs (live stat)"},"crawledPages":{"type":"number","description":"Number of crawled pages (live stat)"},"finished":{"type":"boolean","description":"Whether session has finished"}},"required":["sessionId","configId","domain","startUrls","userId","createdAt"],"title":"CrawlerSessionItem","description":"Crawling session item"},"ListCrawlerSessionsResponse":{"type":"object","properties":{"data":{"type":"array","items":{"$ref":"#/components/schemas/CrawlerSessionItem"},"description":"List of sessions"},"pagination":{"type":"object","properties":{"page":{"type":"number","description":"Current page number"},"pageSize":{"type":"number","description":"Items per page"},"totalItems":{"type":"number","description":"Total number of items"},"totalPages":{"type":"number","description":"Total number of pages"},"hasMore":{"type":"boolean","description":"Whether there are more pages"}},"required":["page","pageSize","totalItems","totalPages","hasMore"],"description":"Pagination metadata"}},"required":["data","pagination"],"title":"ListCrawlerSessionsResponse","description":"Response for listing crawling sessions"},"DataField":{"type":"object","properties":{"mapper":{"type":"string","enum":["jobDescription","categoryClassifier","taxonomyMapping","stableUniqueId","linkExtraction","additionalData","categorize"],"description":"Function that produces this field's value."},"mapperConfig":{"type":"object","additionalProperties":{"nullable":true},"description":"Configuration for the selected mapper."},"name":{"description":"Field name (e.g., productName, 3dListings, listing-count)","type":"string","pattern":"^[^.]*$"},"description":{"type":"string","minLength":1,"description":"Human-readable field description shown in Kadoa."},"instruction":{"type":"string","minLength":1,"description":"Optional field-specific AI instruction. Use this for extraction guidance that is more specific than the description."},"fieldType":{"default":"SCHEMA","type":"string","enum":["SCHEMA"],"description":"Field role. Use SCHEMA for extracted data fields."},"example":{"oneOf":[{"type":"string"},{"type":"array","items":{"type":"string"}}],"description":"Example value for the field"},"shape":{"nullable":true,"description":"Authoritative nested shape for OBJECT/ARRAY fields. Use this for required field structure; without it, a JSON object/array example is promoted to the enforced shape at workflow creation."},"dataType":{"type":"string","description":"Output data type for SCHEMA fields. Use uppercase public values: STRING, NUMBER, BOOLEAN, DATE, DATETIME, MONEY, IMAGE, LINK, OBJECT, ARRAY. Classification fields use fieldType=CLASSIFICATION instead of dataType=CLASSIFICATION. Kadoa-managed functions are not data types; they keep a normal output dataType and carry their function identity in mapper, with configuration in mapperConfig.","enum":["STRING","NUMBER","BOOLEAN","DATE","DATETIME","MONEY","IMAGE","LINK","OBJECT","ARRAY"]},"isKey":{"type":"boolean","description":"Marks this field as part of the record's primary key. Key fields define row identity across runs and enable data linking (records with the same key values are treated as the same record over time, used for dedupe and change detection). Set true ONLY when the complete key tuple uniquely identifies a logical output record and every component is stable across runs and reliably present (not nullable/missing). Key fields should be scalar STRING, NUMBER, or LINK fields; avoid structured, semantic, boolean, image, and timestamp/date fields as keys. Good candidates: external IDs, SKUs, canonical URLs, posting IDs. Bad candidates: prices, counts, timestamps, free-text titles/descriptions, or anything that can change between runs. Multiple fields may form a composite key; uniqueness applies to their combination, not each component. For derived rows, source-backed grouping dimensions and a deterministic output discriminator may identify the result; measured values and explanations do not. If no supported key tuple satisfies these guarantees, leave isKey unset on every field — data linking will simply be disabled, which is preferable to a wrong key. Choosing a non-stable or non-unique key causes duplicate rows and missed updates."}},"required":["name","description","dataType"],"additionalProperties":{"nullable":true},"title":"DataField","description":"Extract and structure specific data from web pages with typed values (e.g., product prices, article titles, dates). `description` explains what the field is; optional `instruction` gives the AI field-specific extraction guidance. Use this for actual data you want to capture. Kadoa-managed functions such as job description, job type classification, taxonomy mapping, and stable unique ID are normal `fieldType: SCHEMA` fields with their output `dataType`; their function identity lives in `mapper`. To expose source values such as the page URL, full HTML, or full Markdown, use a normal `fieldType: SCHEMA` field with `params.sourceKey` (for example `link`, `allExtracts.fullHtml`, or `allExtracts.fullMarkdown`)."},"ClassificationField":{"type":"object","properties":{"name":{"description":"Field name (e.g., category, product-type)","type":"string","pattern":"^[^.]*$"},"description":{"type":"string","minLength":1,"description":"Optional human-readable field description"},"fieldType":{"type":"string","enum":["CLASSIFICATION"],"description":"Field role. Use CLASSIFICATION for predefined category labels."},"categories":{"type":"array","items":{"type":"object","properties":{"title":{"type":"string","description":"Short title/label of the category"},"definition":{"type":"string","description":"Full definition/description of the category"}},"required":["title","definition"]},"description":"List of predefined categories for classification"}},"required":["name","fieldType","categories"],"additionalProperties":true,"title":"ClassificationField","description":"Categorize extracted data into predefined labels. Classification is a field role (`fieldType: CLASSIFICATION`), not a schema data type. Use this when you want the system to classify content into specific categories you define."},"SchemaResponse":{"type":"object","properties":{"id":{"type":"string","description":"Unique identifier for the schema"},"name":{"type":"string","description":"Name of the schema"},"isPublic":{"type":"boolean","description":"Whether the schema is public"},"schema":{"type":"array","items":{"description":"Extraction field schema","discriminator":{"propertyName":"fieldType"},"oneOf":[{"$ref":"#/components/schemas/DataField"},{"$ref":"#/components/schemas/ClassificationField"}]},"description":"Array of field definitions"},"entity":{"type":"string","description":"Entity type for the schema","nullable":true},"description":{"type":"object","properties":{"hintText":{"type":"string","description":"Hint text for the schema"}},"required":["hintText"],"description":"Schema description metadata"}},"required":["id","name","isPublic","schema","entity","description"],"title":"SchemaResponse","description":"Schema object response"},"SchemasListResponse":{"type":"object","properties":{"error":{"type":"boolean","enum":[false],"description":"Error flag (always false on success)"},"data":{"type":"array","items":{"$ref":"#/components/schemas/SchemaResponse"},"description":"Array of schemas"}},"required":["error","data"],"title":"SchemasListResponse","description":"Response wrapper for list of schemas"},"SchemaDataResponse":{"type":"object","properties":{"error":{"type":"boolean","enum":[false],"description":"Error flag (always false on success)"},"data":{"type":"object","properties":{"id":{"type":"string","description":"Unique identifier for the schema"},"name":{"type":"string","description":"Name of the schema"},"isPublic":{"type":"boolean","description":"Whether the schema is public"},"schema":{"type":"array","items":{"description":"Extraction field schema","discriminator":{"propertyName":"fieldType"},"oneOf":[{"$ref":"#/components/schemas/DataField"},{"$ref":"#/components/schemas/ClassificationField"}]},"description":"Array of field definitions"},"entity":{"type":"string","description":"Entity type for the schema","nullable":true},"description":{"type":"object","properties":{"hintText":{"type":"string","description":"Hint text for the schema"}},"required":["hintText"],"description":"Schema description metadata"}},"required":["id","name","isPublic","schema","entity","description"],"description":"Schema data"}},"required":["error","data"],"title":"SchemaDataResponse","description":"Response wrapper for a single schema"},"CreateSchemaBody":{"type":"object","properties":{"name":{"type":"string","minLength":1,"maxLength":255,"description":"Name of the schema"},"entity":{"type":"string","minLength":1,"description":"Entity type for the schema"},"fields":{"type":"array","items":{"description":"Extraction field schema","discriminator":{"propertyName":"fieldType"},"oneOf":[{"$ref":"#/components/schemas/DataField"},{"$ref":"#/components/schemas/ClassificationField"}]},"minItems":1,"description":"Schema fields for extraction - choose from Data Field (typed data) or Classification Field"}},"required":["name","fields"],"title":"CreateSchemaBody","description":"Request body for creating a new schema"},"CreateSchemaResponse":{"type":"object","properties":{"error":{"type":"boolean","enum":[false],"description":"Error flag (always false on success)"},"success":{"type":"boolean","description":"Success flag"},"schemaId":{"type":"string","description":"ID of the created schema"},"message":{"type":"string","description":"Success message"},"createdAt":{"type":"string","description":"Creation timestamp"},"updatedAt":{"type":"string","description":"Last update timestamp"}},"required":["error","success","schemaId","message"],"title":"CreateSchemaResponse","description":"Response for schema creation"},"UpdateSchemaBody":{"type":"object","properties":{"name":{"type":"string","minLength":1,"maxLength":255,"description":"Name of the schema"},"entity":{"type":"string","minLength":1,"description":"Entity type for the schema","nullable":true},"fields":{"type":"array","items":{"description":"Extraction field schema","discriminator":{"propertyName":"fieldType"},"oneOf":[{"$ref":"#/components/schemas/DataField"},{"$ref":"#/components/schemas/ClassificationField"}]},"description":"Array of field definitions"}},"title":"UpdateSchemaBody","description":"Request body for updating a schema"},"UpdateSchemaResponse":{"type":"object","properties":{"error":{"type":"boolean","enum":[false],"description":"Error flag (always false on success)"},"success":{"type":"boolean","description":"Success flag"},"message":{"type":"string","description":"Success message"},"updatedSchema":{"type":"object","properties":{"id":{"type":"string","description":"Unique identifier for the schema"},"name":{"type":"string","description":"Name of the schema"},"isPublic":{"type":"boolean","description":"Whether the schema is public"},"schema":{"type":"array","items":{"description":"Extraction field schema","discriminator":{"propertyName":"fieldType"},"oneOf":[{"$ref":"#/components/schemas/DataField"},{"$ref":"#/components/schemas/ClassificationField"}]},"description":"Array of field definitions"},"entity":{"type":"string","description":"Entity type for the schema","nullable":true},"description":{"type":"object","properties":{"hintText":{"type":"string","description":"Hint text for the schema"}},"required":["hintText"],"description":"Schema description metadata"}},"required":["id","name","isPublic","schema","entity","description"],"description":"The updated schema data (returned to avoid read-replica lag)"}},"required":["error","success","message"],"title":"UpdateSchemaResponse","description":"Response for schema update"},"DeleteSchemaResponse":{"type":"object","properties":{"error":{"type":"boolean","enum":[false],"description":"Error flag (always false on success)"},"success":{"type":"boolean","description":"Success flag"},"message":{"type":"string","description":"Success message"}},"required":["error","success","message"],"title":"DeleteSchemaResponse","description":"Response for schema deletion"},"LatestVersionSummary":{"type":"object","properties":{"promptPreview":{"type":"string","description":"Truncated prompt prefix (capped at ~280 chars with ellipsis) for list display. null when the latest version has no prompt.","nullable":true},"schemaFieldNames":{"type":"array","items":{"type":"string"},"description":"Field names of the latest version's schema, in declared order. Empty when the version has no schema."},"dqRuleCount":{"type":"integer","description":"Count of data-quality rule fields on the latest version (top-level keys of schemaValidationRules, which are field names)."},"notificationChannelCount":{"type":"integer","description":"Count of distinct notification channels across all events on the latest version."},"frequencyInterval":{"type":"string","enum":["ONLY_ONCE","EVERY_10_MINUTES","EVERY_20_MINUTES","HALF_HOURLY","HOURLY","TWO_HOURLY","THREE_HOURLY","FOUR_HOURLY","SIX_HOURLY","TWELVE_HOURLY","EIGHTEEN_HOURLY","DAILY","TWO_DAY","THREE_DAY","WEEKLY","BIWEEKLY","TRIWEEKLY","FOUR_WEEKS","MONTHLY","CUSTOM"],"description":"Frequency interval enum of the latest version. null when the version does not control frequency.","nullable":true},"frequencyWeekdaysOnly":{"type":"boolean","description":"Whether the latest version skips Saturday and Sunday runs."}},"required":["promptPreview","schemaFieldNames","dqRuleCount","notificationChannelCount","frequencyInterval","frequencyWeekdaysOnly"],"title":"LatestVersionSummary","description":"Content preview of the latest version for list rendering. null when the template has no published versions; omitted by create/update/duplicate responses."},"TemplateResponse":{"type":"object","properties":{"id":{"type":"string","format":"uuid","description":"Template ID"},"name":{"type":"string","description":"Template name"},"description":{"type":"string","description":"Template description","nullable":true},"teamId":{"type":"string","format":"uuid","description":"Owning team ID"},"latestVersion":{"type":"number","description":"Latest published version number","nullable":true},"workflowCount":{"type":"number","description":"Number of workflows linked to this template"},"latestVersionSummary":{"nullable":true,"allOf":[{"$ref":"#/components/schemas/LatestVersionSummary"}]},"archivedAt":{"type":"string","description":"Archive timestamp (null if active)","nullable":true},"createdAt":{"type":"string","description":"Creation timestamp"},"updatedAt":{"type":"string","description":"Last update timestamp"}},"required":["id","name","description","teamId","latestVersion","archivedAt","createdAt","updatedAt"],"title":"TemplateResponse","description":"Template object response"},"TemplateListResponse":{"type":"object","properties":{"error":{"type":"boolean","enum":[false],"description":"Error flag (always false on success)"},"data":{"type":"array","items":{"$ref":"#/components/schemas/TemplateResponse"},"description":"List of templates"}},"required":["error","data"],"title":"TemplateListResponse","description":"Response wrapper for list of templates"},"TemplateDetailResponseBody":{"type":"object","properties":{"error":{"type":"boolean","enum":[false],"description":"Error flag (always false on success)"},"data":{"type":"object","properties":{"id":{"type":"string","format":"uuid","description":"Template ID"},"name":{"type":"string","description":"Template name"},"description":{"type":"string","description":"Template description","nullable":true},"teamId":{"type":"string","format":"uuid","description":"Owning team ID"},"latestVersion":{"type":"number","description":"Latest published version number","nullable":true},"workflowCount":{"type":"number","description":"Number of workflows linked to this template"},"latestVersionSummary":{"nullable":true,"allOf":[{"$ref":"#/components/schemas/LatestVersionSummary"}]},"archivedAt":{"type":"string","description":"Archive timestamp (null if active)","nullable":true},"createdAt":{"type":"string","description":"Creation timestamp"},"updatedAt":{"type":"string","description":"Last update timestamp"},"versions":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string","format":"uuid","description":"Version row ID"},"templateId":{"type":"string","format":"uuid","description":"Parent template ID"},"version":{"type":"number","description":"Version number"},"name":{"type":"string","description":"Custom display name (null = default 'v.N')","nullable":true},"publisher":{"type":"object","properties":{"kind":{"type":"string","enum":["HUMAN","SERVICE_ACCOUNT","AGENT","SYSTEM"],"description":"Publisher kind; null for legacy/unproven versions","nullable":true},"label":{"type":"string","description":"Current human name/email, non-human publisher label, or Unknown for legacy/unproven versions"}},"required":["kind","label"],"description":"Publisher attribution"},"prompt":{"type":"string","description":"User prompt","nullable":true},"schemaId":{"type":"string","format":"uuid","description":"Referenced data_schemas ID","nullable":true},"schemaFields":{"type":"array","items":{"type":"object","properties":{"mapper":{"type":"string","enum":["jobDescription","categoryClassifier","taxonomyMapping","stableUniqueId","linkExtraction","additionalData","categorize"],"description":"Function that produces this field's value."},"mapperConfig":{"type":"object","additionalProperties":{"nullable":true},"description":"Configuration for the selected mapper."},"name":{"type":"string","description":"Field name"},"description":{"type":"string","description":"Human-readable field description shown in Kadoa"},"instruction":{"type":"string","description":"Optional field-specific AI instruction for extraction guidance"},"fieldType":{"type":"string","description":"Field role (SCHEMA or CLASSIFICATION)"},"example":{"nullable":true,"description":"Example value (string, array, or object for OBJECT/ARRAY dataTypes)"},"shape":{"nullable":true,"description":"Authoritative nested shape for OBJECT/ARRAY fields; without it, a JSON object/array example is promoted to the enforced shape at workflow creation."},"dataType":{"type":"string","description":"Output data type for SCHEMA fields. Use public values such as STRING, NUMBER, BOOLEAN, DATE, DATETIME, MONEY, IMAGE, LINK, OBJECT, or ARRAY."},"isKey":{"type":"boolean","description":"Marks this field as part of the record's primary key. Key fields define row identity across runs and enable data linking (records with the same key values are treated as the same record over time, used for dedupe and change detection). Set true ONLY when the complete key tuple uniquely identifies a logical output record and every component is stable across runs and reliably present (not nullable/missing). Key fields should be scalar STRING, NUMBER, or LINK fields; avoid structured, semantic, boolean, image, and timestamp/date fields as keys. Good candidates: external IDs, SKUs, canonical URLs, posting IDs. Bad candidates: prices, counts, timestamps, free-text titles/descriptions, or anything that can change between runs. Multiple fields may form a composite key; uniqueness applies to their combination, not each component. For derived rows, source-backed grouping dimensions and a deterministic output discriminator may identify the result; measured values and explanations do not. If no supported key tuple satisfies these guarantees, leave isKey unset on every field — data linking will simply be disabled, which is preferable to a wrong key. Choosing a non-stable or non-unique key causes duplicate rows and missed updates."},"categories":{"type":"array","items":{"type":"object","properties":{"title":{"type":"string","description":"Short title/label of the category"},"definition":{"type":"string","description":"Full definition/description of the category"}},"required":["title","definition"]},"description":"Predefined categories for CLASSIFICATION fields"}},"required":["name"],"additionalProperties":{"nullable":true}},"nullable":true,"description":"Resolved schema fields from data_schemas"},"schemaValidationRules":{"type":"object","additionalProperties":{"type":"object","additionalProperties":{"nullable":true}},"description":"Schema validation rules for this version","nullable":true},"notifications":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string","format":"uuid","description":"Notification configuration ID"},"eventType":{"type":"string","description":"Event type (e.g., workflow_finished, error)"},"eventConfiguration":{"type":"object","additionalProperties":{"nullable":true},"description":"Event-specific config"},"enabled":{"type":"boolean","description":"Whether this notification is enabled"},"channels":{"type":"array","items":{"type":"object","properties":{"channelId":{"type":"string","format":"uuid"},"channelName":{"type":"string"},"channelType":{"type":"string"}},"required":["channelId","channelName","channelType"]},"description":"Linked notification channels"}},"required":["id","eventType","eventConfiguration","enabled","channels"]}},"frequency":{"type":"object","properties":{"interval":{"type":"string","enum":["ONLY_ONCE","EVERY_10_MINUTES","EVERY_20_MINUTES","HALF_HOURLY","HOURLY","TWO_HOURLY","THREE_HOURLY","FOUR_HOURLY","SIX_HOURLY","TWELVE_HOURLY","EIGHTEEN_HOURLY","DAILY","TWO_DAY","THREE_DAY","WEEKLY","BIWEEKLY","TRIWEEKLY","FOUR_WEEKS","MONTHLY","CUSTOM"],"description":"Update interval enum (HOURLY/DAILY/CUSTOM/...). When CUSTOM, schedules must be provided."},"schedules":{"type":"array","items":{"type":"object","properties":{"type":{"type":"string","enum":["repeat","cron"],"description":"Schedule type"},"interval":{"type":"string","description":"Repeat token (e.g., '1h', '1d') when type=repeat"},"expressions":{"type":"array","items":{"type":"string"},"description":"Cron expressions when type=cron"},"timezone":{"type":"string","description":"IANA timezone for cron expressions (e.g. 'America/New_York'). Defaults to UTC."}},"required":["type"]},"description":"Cron/repeat schedule specs. Required when interval=CUSTOM."},"weekdaysOnly":{"type":"boolean","description":"Skip runs that fall on Saturday or Sunday. Applies only to repeat intervals; for cron, set the weekdays in the expression."}},"description":"Frequency configuration for this version","nullable":true},"recordLimit":{"type":"integer","minimum":1,"maximum":2147483647,"nullable":true,"description":"Immutable output record limit; null when managed unlimited or unmanaged"},"recordLimitManaged":{"type":"boolean","description":"Whether this version owns the workflow output record limit"},"createdAt":{"type":"string","description":"Creation timestamp"},"schemaName":{"type":"string","nullable":true,"description":"Name of the linked schema"},"schemaEntity":{"type":"string","nullable":true,"description":"Entity name from the linked schema"}},"required":["id","templateId","version","name","publisher","prompt","schemaId","frequency","createdAt"]},"description":"All published versions"}},"required":["id","name","description","teamId","latestVersion","archivedAt","createdAt","updatedAt","versions"],"description":"Template with versions"}},"required":["error","data"],"title":"TemplateDetailResponseBody","description":"Response wrapper for template detail"},"CreateTemplateBody":{"type":"object","properties":{"name":{"type":"string","minLength":1,"maxLength":255,"description":"Name of the template"},"description":{"type":"string","maxLength":2000,"description":"Description of the template"}},"required":["name"],"title":"CreateTemplateBody","description":"Request body for creating a new template"},"TemplateCreatedResponse":{"type":"object","properties":{"error":{"type":"boolean","enum":[false],"description":"Error flag (always false on success)"},"success":{"type":"boolean","enum":[true],"description":"Success flag"},"data":{"type":"object","properties":{"id":{"type":"string","format":"uuid","description":"Template ID"},"name":{"type":"string","description":"Template name"},"description":{"type":"string","description":"Template description","nullable":true},"teamId":{"type":"string","format":"uuid","description":"Owning team ID"},"latestVersion":{"type":"number","description":"Latest published version number","nullable":true},"workflowCount":{"type":"number","description":"Number of workflows linked to this template"},"latestVersionSummary":{"nullable":true,"allOf":[{"$ref":"#/components/schemas/LatestVersionSummary"}]},"archivedAt":{"type":"string","description":"Archive timestamp (null if active)","nullable":true},"createdAt":{"type":"string","description":"Creation timestamp"},"updatedAt":{"type":"string","description":"Last update timestamp"}},"required":["id","name","description","teamId","latestVersion","archivedAt","createdAt","updatedAt"],"description":"Created template"}},"required":["error","success","data"],"title":"TemplateCreatedResponse","description":"Response for template creation"},"UpdateTemplateBody":{"type":"object","properties":{"name":{"type":"string","minLength":1,"maxLength":255,"description":"Updated name"},"description":{"type":"string","maxLength":2000,"nullable":true,"description":"Updated description"}},"title":"UpdateTemplateBody","description":"Request body for updating a template"},"TemplateUpdatedResponse":{"type":"object","properties":{"error":{"type":"boolean","enum":[false],"description":"Error flag (always false on success)"},"success":{"type":"boolean","enum":[true],"description":"Success flag"},"data":{"type":"object","properties":{"id":{"type":"string","format":"uuid","description":"Template ID"},"name":{"type":"string","description":"Template name"},"description":{"type":"string","description":"Template description","nullable":true},"teamId":{"type":"string","format":"uuid","description":"Owning team ID"},"latestVersion":{"type":"number","description":"Latest published version number","nullable":true},"workflowCount":{"type":"number","description":"Number of workflows linked to this template"},"latestVersionSummary":{"nullable":true,"allOf":[{"$ref":"#/components/schemas/LatestVersionSummary"}]},"archivedAt":{"type":"string","description":"Archive timestamp (null if active)","nullable":true},"createdAt":{"type":"string","description":"Creation timestamp"},"updatedAt":{"type":"string","description":"Last update timestamp"}},"required":["id","name","description","teamId","latestVersion","archivedAt","createdAt","updatedAt"],"description":"Updated template"}},"required":["error","success","data"],"title":"TemplateUpdatedResponse","description":"Response for template update"},"TemplateArchivedResponse":{"type":"object","properties":{"error":{"type":"boolean","enum":[false],"description":"Error flag (always false on success)"},"success":{"type":"boolean","enum":[true],"description":"Success flag"},"message":{"type":"string","description":"Archive confirmation message"},"unlinkedWorkflowCount":{"type":"integer","minimum":0,"description":"Number of workflows unlinked by this archive"}},"required":["error","success","message","unlinkedWorkflowCount"],"title":"TemplateArchivedResponse","description":"Response for template archival"},"DuplicateTemplateBody":{"type":"object","properties":{"name":{"type":"string","minLength":1,"maxLength":255,"description":"Name for the duplicate. Defaults to the source name with a collision-safe \"(Copy)\" suffix."}},"title":"DuplicateTemplateBody","description":"Request body for duplicating a template (all versions and configs, no linked workflows)"},"CreateTemplateVersionBody":{"type":"object","properties":{"prompt":{"type":"string","nullable":true,"description":"Prompt; omit to inherit, null to clear"},"schemaId":{"type":"string","format":"uuid","nullable":true,"description":"Schema ID; omit to inherit, null to clear (mutually exclusive with schemaFields)"},"schemaFields":{"type":"array","items":{"type":"object","properties":{"mapper":{"type":"string","enum":["jobDescription","categoryClassifier","taxonomyMapping","stableUniqueId","linkExtraction","additionalData","categorize"],"description":"Function that produces this field's value."},"mapperConfig":{"type":"object","additionalProperties":{"nullable":true},"description":"Configuration for the selected mapper."},"name":{"type":"string","description":"Field name"},"description":{"type":"string","description":"Human-readable field description shown in Kadoa"},"instruction":{"type":"string","description":"Optional field-specific AI instruction for extraction guidance"},"fieldType":{"type":"string","description":"Field role (SCHEMA or CLASSIFICATION)"},"example":{"nullable":true,"description":"Example value (string, array, or object for OBJECT/ARRAY dataTypes)"},"shape":{"nullable":true,"description":"Authoritative nested shape for OBJECT/ARRAY fields; without it, a JSON object/array example is promoted to the enforced shape at workflow creation."},"dataType":{"type":"string","description":"Output data type for SCHEMA fields. Use public values such as STRING, NUMBER, BOOLEAN, DATE, DATETIME, MONEY, IMAGE, LINK, OBJECT, or ARRAY."},"isKey":{"type":"boolean","description":"Marks this field as part of the record's primary key. Key fields define row identity across runs and enable data linking (records with the same key values are treated as the same record over time, used for dedupe and change detection). Set true ONLY when the complete key tuple uniquely identifies a logical output record and every component is stable across runs and reliably present (not nullable/missing). Key fields should be scalar STRING, NUMBER, or LINK fields; avoid structured, semantic, boolean, image, and timestamp/date fields as keys. Good candidates: external IDs, SKUs, canonical URLs, posting IDs. Bad candidates: prices, counts, timestamps, free-text titles/descriptions, or anything that can change between runs. Multiple fields may form a composite key; uniqueness applies to their combination, not each component. For derived rows, source-backed grouping dimensions and a deterministic output discriminator may identify the result; measured values and explanations do not. If no supported key tuple satisfies these guarantees, leave isKey unset on every field — data linking will simply be disabled, which is preferable to a wrong key. Choosing a non-stable or non-unique key causes duplicate rows and missed updates."},"categories":{"type":"array","items":{"type":"object","properties":{"title":{"type":"string","description":"Short title/label of the category"},"definition":{"type":"string","description":"Full definition/description of the category"}},"required":["title","definition"]},"description":"Predefined categories for CLASSIFICATION fields"}},"required":["name"],"additionalProperties":{"nullable":true}},"nullable":true,"description":"Inline schema fields; omit to inherit, null to clear"},"schemaEntity":{"type":"string","description":"Entity name for supplied inline schema fields"},"schemaValidationRules":{"type":"object","additionalProperties":{"type":"object","additionalProperties":{"nullable":true}},"description":"Rules; omit to inherit rules for fields retained by a replacement schema, null to clear, {} to manage an empty ruleset","nullable":true},"notifications":{"type":"array","items":{"type":"object","properties":{"eventType":{"type":"string"},"eventConfiguration":{"type":"object","additionalProperties":{"nullable":true}},"enabled":{"type":"boolean"},"channelIds":{"type":"array","items":{"type":"string","format":"uuid"}},"channels":{"type":"array","items":{"type":"object","properties":{"channelId":{"type":"string","format":"uuid"}},"required":["channelId"]}}},"required":["eventType"]},"nullable":true,"description":"Notifications; omit to inherit, null or [] to clear"},"frequency":{"type":"object","properties":{"interval":{"type":"string","enum":["ONLY_ONCE","EVERY_10_MINUTES","EVERY_20_MINUTES","HALF_HOURLY","HOURLY","TWO_HOURLY","THREE_HOURLY","FOUR_HOURLY","SIX_HOURLY","TWELVE_HOURLY","EIGHTEEN_HOURLY","DAILY","TWO_DAY","THREE_DAY","WEEKLY","BIWEEKLY","TRIWEEKLY","FOUR_WEEKS","MONTHLY","CUSTOM"],"description":"Update interval enum (HOURLY/DAILY/CUSTOM/...). When CUSTOM, schedules must be provided."},"schedules":{"type":"array","items":{"type":"object","properties":{"type":{"type":"string","enum":["repeat","cron"],"description":"Schedule type"},"interval":{"type":"string","description":"Repeat token (e.g., '1h', '1d') when type=repeat"},"expressions":{"type":"array","items":{"type":"string"},"description":"Cron expressions when type=cron"},"timezone":{"type":"string","description":"IANA timezone for cron expressions (e.g. 'America/New_York'). Defaults to UTC."}},"required":["type"]},"description":"Cron/repeat schedule specs. Required when interval=CUSTOM."},"weekdaysOnly":{"type":"boolean","description":"Skip runs that fall on Saturday or Sunday. Applies only to repeat intervals; for cron, set the weekdays in the expression."}},"nullable":true,"description":"Frequency; omit to inherit, null to clear"},"recordLimit":{"type":"integer","minimum":1,"maximum":2147483647,"nullable":true,"description":"Output record limit; omit to inherit, null for template-managed unlimited"},"recordLimitManaged":{"type":"boolean","enum":[false],"description":"False clears template ownership of the output record limit"}},"title":"CreateTemplateVersionBody","description":"Publish a complete immutable template snapshot. Omitted components inherit from the preceding version; null explicitly clears a component."},"TemplateVersionMutationResponse":{"type":"object","properties":{"error":{"type":"boolean","enum":[false],"description":"Error flag (always false on success)"},"success":{"type":"boolean","enum":[true],"description":"Success flag"},"data":{"type":"object","properties":{"id":{"type":"string","format":"uuid","description":"Version row ID"},"templateId":{"type":"string","format":"uuid","description":"Parent template ID"},"version":{"type":"number","description":"Version number"},"name":{"type":"string","description":"Custom display name (null = default 'v.N')","nullable":true},"publisher":{"type":"object","properties":{"kind":{"type":"string","enum":["HUMAN","SERVICE_ACCOUNT","AGENT","SYSTEM"],"description":"Publisher kind; null for legacy/unproven versions","nullable":true},"label":{"type":"string","description":"Current human name/email, non-human publisher label, or Unknown for legacy/unproven versions"}},"required":["kind","label"],"description":"Publisher attribution"},"prompt":{"type":"string","description":"User prompt","nullable":true},"schemaId":{"type":"string","format":"uuid","description":"Referenced data_schemas ID","nullable":true},"schemaFields":{"type":"array","items":{"type":"object","properties":{"mapper":{"type":"string","enum":["jobDescription","categoryClassifier","taxonomyMapping","stableUniqueId","linkExtraction","additionalData","categorize"],"description":"Function that produces this field's value."},"mapperConfig":{"type":"object","additionalProperties":{"nullable":true},"description":"Configuration for the selected mapper."},"name":{"type":"string","description":"Field name"},"description":{"type":"string","description":"Human-readable field description shown in Kadoa"},"instruction":{"type":"string","description":"Optional field-specific AI instruction for extraction guidance"},"fieldType":{"type":"string","description":"Field role (SCHEMA or CLASSIFICATION)"},"example":{"nullable":true,"description":"Example value (string, array, or object for OBJECT/ARRAY dataTypes)"},"shape":{"nullable":true,"description":"Authoritative nested shape for OBJECT/ARRAY fields; without it, a JSON object/array example is promoted to the enforced shape at workflow creation."},"dataType":{"type":"string","description":"Output data type for SCHEMA fields. Use public values such as STRING, NUMBER, BOOLEAN, DATE, DATETIME, MONEY, IMAGE, LINK, OBJECT, or ARRAY."},"isKey":{"type":"boolean","description":"Marks this field as part of the record's primary key. Key fields define row identity across runs and enable data linking (records with the same key values are treated as the same record over time, used for dedupe and change detection). Set true ONLY when the complete key tuple uniquely identifies a logical output record and every component is stable across runs and reliably present (not nullable/missing). Key fields should be scalar STRING, NUMBER, or LINK fields; avoid structured, semantic, boolean, image, and timestamp/date fields as keys. Good candidates: external IDs, SKUs, canonical URLs, posting IDs. Bad candidates: prices, counts, timestamps, free-text titles/descriptions, or anything that can change between runs. Multiple fields may form a composite key; uniqueness applies to their combination, not each component. For derived rows, source-backed grouping dimensions and a deterministic output discriminator may identify the result; measured values and explanations do not. If no supported key tuple satisfies these guarantees, leave isKey unset on every field — data linking will simply be disabled, which is preferable to a wrong key. Choosing a non-stable or non-unique key causes duplicate rows and missed updates."},"categories":{"type":"array","items":{"type":"object","properties":{"title":{"type":"string","description":"Short title/label of the category"},"definition":{"type":"string","description":"Full definition/description of the category"}},"required":["title","definition"]},"description":"Predefined categories for CLASSIFICATION fields"}},"required":["name"],"additionalProperties":{"nullable":true}},"nullable":true,"description":"Resolved schema fields from data_schemas"},"schemaValidationRules":{"type":"object","additionalProperties":{"type":"object","additionalProperties":{"nullable":true}},"description":"Schema validation rules for this version","nullable":true},"notifications":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string","format":"uuid","description":"Notification configuration ID"},"eventType":{"type":"string","description":"Event type (e.g., workflow_finished, error)"},"eventConfiguration":{"type":"object","additionalProperties":{"nullable":true},"description":"Event-specific config"},"enabled":{"type":"boolean","description":"Whether this notification is enabled"},"channels":{"type":"array","items":{"type":"object","properties":{"channelId":{"type":"string","format":"uuid"},"channelName":{"type":"string"},"channelType":{"type":"string"}},"required":["channelId","channelName","channelType"]},"description":"Linked notification channels"}},"required":["id","eventType","eventConfiguration","enabled","channels"]}},"frequency":{"type":"object","properties":{"interval":{"type":"string","enum":["ONLY_ONCE","EVERY_10_MINUTES","EVERY_20_MINUTES","HALF_HOURLY","HOURLY","TWO_HOURLY","THREE_HOURLY","FOUR_HOURLY","SIX_HOURLY","TWELVE_HOURLY","EIGHTEEN_HOURLY","DAILY","TWO_DAY","THREE_DAY","WEEKLY","BIWEEKLY","TRIWEEKLY","FOUR_WEEKS","MONTHLY","CUSTOM"],"description":"Update interval enum (HOURLY/DAILY/CUSTOM/...). When CUSTOM, schedules must be provided."},"schedules":{"type":"array","items":{"type":"object","properties":{"type":{"type":"string","enum":["repeat","cron"],"description":"Schedule type"},"interval":{"type":"string","description":"Repeat token (e.g., '1h', '1d') when type=repeat"},"expressions":{"type":"array","items":{"type":"string"},"description":"Cron expressions when type=cron"},"timezone":{"type":"string","description":"IANA timezone for cron expressions (e.g. 'America/New_York'). Defaults to UTC."}},"required":["type"]},"description":"Cron/repeat schedule specs. Required when interval=CUSTOM."},"weekdaysOnly":{"type":"boolean","description":"Skip runs that fall on Saturday or Sunday. Applies only to repeat intervals; for cron, set the weekdays in the expression."}},"description":"Frequency configuration for this version","nullable":true},"recordLimit":{"type":"integer","minimum":1,"maximum":2147483647,"nullable":true,"description":"Immutable output record limit; null when managed unlimited or unmanaged"},"recordLimitManaged":{"type":"boolean","description":"Whether this version owns the workflow output record limit"},"createdAt":{"type":"string","description":"Creation timestamp"}},"required":["id","templateId","version","name","publisher","prompt","schemaId","frequency","createdAt"],"description":"Template version"}},"required":["error","success","data"],"title":"TemplateVersionMutationResponse","description":"Response for template version create/update"},"UpdateTemplateVersionBody":{"type":"object","properties":{"name":{"description":"Custom display name. null, 'null', empty, or whitespace clears the name and restores the default 'v.N' label.","type":"string","maxLength":100,"nullable":true}},"required":["name"],"title":"UpdateTemplateVersionBody","description":"Request body for renaming a template version"},"TemplateSchemasResponse":{"type":"object","properties":{"error":{"type":"boolean","enum":[false],"description":"Error flag (always false on success)"},"data":{"type":"array","items":{"type":"object","properties":{"schemaId":{"type":"string","format":"uuid","description":"Schema ID"},"schemaName":{"type":"string","description":"Schema name"},"entity":{"type":"string","description":"Entity name","nullable":true},"fieldCount":{"type":"number","description":"Number of fields in the schema"}},"required":["schemaId","schemaName","entity","fieldCount"]},"description":"Schemas linked to this template"}},"required":["error","data"],"title":"TemplateSchemasResponse","description":"Response for listing schemas linked to a template"},"TemplateWorkflowsResponse":{"type":"object","properties":{"error":{"type":"boolean","enum":[false],"description":"Error flag (always false on success)"},"data":{"type":"array","items":{"type":"object","properties":{"workflowId":{"type":"string","format":"uuid","description":"Workflow ID"},"workflowName":{"type":"string","description":"Workflow name"},"templateVersion":{"type":"number","description":"Template version the workflow was created from"},"isOutdated":{"type":"boolean","description":"Whether a newer template version exists"},"state":{"type":"string","description":"Current workflow state"}},"required":["workflowId","workflowName","templateVersion","isOutdated","state"]},"description":"Workflows linked to this template"}},"required":["error","data"],"title":"TemplateWorkflowsResponse","description":"Response for listing workflows created from a template"},"ApplyTemplateUpdateBody":{"type":"object","properties":{"targetVersion":{"type":"integer","minimum":1,"description":"Template version to apply"},"workflowIds":{"type":"array","items":{"type":"string","format":"uuid"},"minItems":1,"maxItems":2000,"description":"Workflow IDs to update (max 2000)"}},"required":["targetVersion","workflowIds"],"title":"ApplyTemplateUpdateBody","description":"Request body for applying a template version update to existing workflows"},"ApplyTemplateUpdateResponse":{"type":"object","properties":{"error":{"type":"boolean","enum":[false],"description":"Error flag (always false on success)"},"success":{"type":"boolean","enum":[true],"description":"Success flag"},"updatedCount":{"type":"number","description":"Number of workflows updated"},"workflowIds":{"type":"array","items":{"type":"string","format":"uuid"},"description":"IDs of updated workflows"},"controlledParts":{"type":"object","properties":{"prompt":{"type":"boolean","description":"Whether the template controlled the prompt"},"schema":{"type":"boolean","description":"Whether the template controlled the schema"},"schemaValidationRules":{"type":"boolean","description":"Whether the template controlled the schema validation rules"},"notifications":{"type":"boolean","description":"Whether the template controlled notifications"},"frequency":{"type":"boolean","description":"Whether the template controlled the frequency"}},"required":["prompt","schema","schemaValidationRules","notifications","frequency"],"description":"Which workflow parts were updated by this template version"}},"required":["error","success","updatedCount","workflowIds","controlledParts"],"title":"ApplyTemplateUpdateResponse","description":"Response for template update application"},"SchemaChangePreviewBody":{"type":"object","properties":{"workflowId":{"type":"string","format":"uuid","description":"Linked workflow to preview"},"targetVersion":{"type":"integer","minimum":1,"description":"Template version to preview"}},"required":["workflowId","targetVersion"],"title":"SchemaChangePreviewBody","description":"Request body for previewing a schema change without applying it"},"SchemaChangePreviewResponse":{"type":"object","properties":{"error":{"type":"boolean","enum":[false],"description":"Error flag (always false on success)"},"data":{"type":"object","properties":{"workflowId":{"type":"string","format":"uuid"},"workflowName":{"type":"string"},"currentVersion":{"type":"integer","minimum":1},"targetVersion":{"type":"integer","minimum":1},"basis":{"type":"string","enum":["existing_data","configuration_only"]},"columns":{"type":"array","items":{"type":"object","properties":{"name":{"type":"string","minLength":1},"label":{"type":"string","minLength":1},"dataType":{"type":"string","minLength":1,"description":"Target datatype, or the previous datatype for a removed field"},"previousDataType":{"type":"string","minLength":1,"description":"Effective datatype before the schema change, if any","nullable":true},"beforeValueSource":{"type":"string","enum":["observed","none"],"description":"Where the before value came from: observed in stored output, or none"},"afterValueSource":{"type":"string","enum":["observed","simulated","none"],"description":"Where the after value came from: observed, simulated by the model, or none"},"truncated":{"type":"boolean","description":"Whether a value for this field was truncated to fit the preview budget; absent means not truncated"},"status":{"type":"string","enum":["unchanged","removed","added","updated"]}},"required":["name","label","dataType","previousDataType","beforeValueSource","afterValueSource","status"]}},"beforeRows":{"type":"array","items":{"type":"object","additionalProperties":{"nullable":true}},"maxItems":10},"rows":{"type":"array","items":{"type":"object","additionalProperties":{"nullable":true}},"maxItems":10},"truncated":{"type":"boolean","description":"Whether any preview value was truncated to fit the data budget"}},"required":["workflowId","workflowName","currentVersion","targetVersion","basis","columns","beforeRows","rows","truncated"]}},"required":["error","data"],"title":"SchemaChangePreviewResponse","description":"Read-only AI-generated preview of how a schema change affects one linked workflow's data"},"LinkWorkflowsBody":{"type":"object","properties":{"workflowIds":{"type":"array","items":{"type":"string","format":"uuid"},"minItems":1,"maxItems":2000,"description":"Workflow IDs to link to this template"},"force":{"type":"boolean","description":"If true, relink workflows that are already linked to another template"}},"required":["workflowIds"],"title":"LinkWorkflowsBody","description":"Request body for linking workflows to a template"},"LinkWorkflowsResponse":{"type":"object","properties":{"error":{"type":"boolean","enum":[false],"description":"Error flag (always false on success)"},"success":{"type":"boolean","enum":[true],"description":"Success flag"},"linkedCount":{"type":"number","description":"Number of workflows linked"},"workflowIds":{"type":"array","items":{"type":"string","format":"uuid"},"description":"IDs of linked workflows"}},"required":["error","success","linkedCount","workflowIds"],"title":"LinkWorkflowsResponse","description":"Response for linking workflows to a template"},"LinkWorkflowsConflictResponse":{"type":"object","properties":{"error":{"type":"boolean","enum":[true],"description":"Error flag"},"code":{"type":"string","enum":["CONFLICT"],"description":"Error code"},"conflicts":{"type":"array","items":{"type":"object","properties":{"workflowId":{"type":"string","format":"uuid"},"workflowName":{"type":"string"},"templateId":{"type":"string","format":"uuid"},"templateName":{"type":"string"}},"required":["workflowId","workflowName","templateId","templateName"]},"description":"Workflows already linked to another template"}},"required":["error","code","conflicts"],"title":"LinkWorkflowsConflictResponse","description":"Response when workflows are already linked to another template"},"SaveFromWorkflowBody":{"type":"object","properties":{"workflowId":{"type":"string","format":"uuid","description":"Source workflow ID to extract config from"},"name":{"type":"string","minLength":1,"maxLength":255,"description":"Name for the new template (required if templateId is not set)"},"description":{"type":"string","maxLength":2000,"description":"Description for the new template"},"templateId":{"type":"string","format":"uuid","description":"Existing template ID to add a new version to (mutually exclusive with name)"},"includeParts":{"type":"array","items":{"type":"string","enum":["prompt","schema","schemaValidationRules","notifications","frequency","recordLimit"]},"minItems":1,"description":"Which workflow parts to include in the template. If omitted, all parts are included."}},"required":["workflowId"],"title":"SaveFromWorkflowBody","description":"Request body for saving a workflow's config as a template (new or existing)"},"SaveFromWorkflowResponse":{"type":"object","properties":{"error":{"type":"boolean","enum":[false],"description":"Error flag (always false on success)"},"success":{"type":"boolean","enum":[true],"description":"Success flag"},"data":{"type":"object","properties":{"templateId":{"type":"string","format":"uuid","description":"Template ID (new or existing)"},"version":{"type":"number","description":"Published version number"},"isNew":{"type":"boolean","description":"Whether a new template was created"}},"required":["templateId","version","isNew"]}},"required":["error","success","data"],"title":"SaveFromWorkflowResponse","description":"Response for saving a workflow as a template"},"UnlinkWorkflowsBody":{"type":"object","properties":{"workflowIds":{"type":"array","items":{"type":"string","format":"uuid"},"minItems":1,"maxItems":2000,"description":"Workflow IDs to unlink from this template"}},"required":["workflowIds"],"title":"UnlinkWorkflowsBody","description":"Request body for unlinking workflows from a template"},"UnlinkWorkflowsResponse":{"type":"object","properties":{"error":{"type":"boolean","enum":[false],"description":"Error flag (always false on success)"},"success":{"type":"boolean","enum":[true],"description":"Success flag"},"unlinkedCount":{"type":"number","description":"Number of workflows unlinked"},"workflowIds":{"type":"array","items":{"type":"string","format":"uuid"},"description":"IDs of unlinked workflows"}},"required":["error","success","unlinkedCount","workflowIds"],"title":"UnlinkWorkflowsResponse","description":"Response for unlinking workflows from a template"},"Location":{"type":"object","properties":{"type":{"type":"string","enum":["auto","manual"],"description":"Location type"},"isoCode":{"type":"string","description":"Country ISO code for manual location"}},"required":["type"],"title":"Location","description":"Geographic location for scraping. Use 'auto' for automatic detection or 'manual' to specify a country"},"BrowserInteraction":{"type":"object","properties":{"type":{"type":"string","enum":["CLICK","TYPE","HOVER","SCROLL","WAIT","KEYPRESS","LOAD","SELECT","BACKSPACE","ENTER","TAB","DELETE","GOTO","REFRESH","NAVIGATE_BACK"],"description":"Type of interaction"},"selector":{"type":"string","description":"CSS selector for the target element (required for CLICK, HOVER)"},"text":{"type":"string","description":"Text to type (required for TYPE)"},"timeMs":{"type":"number","description":"Time in milliseconds (required for WAIT)"},"url":{"type":"string","description":"URL to navigate to (required for GOTO)"},"tagName":{"type":"string","description":"HTML tag name of the element"},"innerText":{"type":"string","description":"Inner text content of the element"}},"required":["type"],"additionalProperties":true,"title":"BrowserInteraction","description":"Browser interaction definition. Examples:\n- CLICK: {type: 'CLICK', selector: '#submit-btn'}\n- TYPE: {type: 'TYPE', text: 'hello world'}\n- WAIT: {type: 'WAIT', timeMs: 2000}\n- GOTO: {type: 'GOTO', url: 'https://example.com'}\n- ENTER/TAB/BACKSPACE/DELETE/REFRESH/NAVIGATE_BACK/SCROLL/HOVER/SELECT/LOAD/KEYPRESS: {type: 'ENTER'} (no additional parameters needed)"},"WebExtensionInteraction":{"type":"object","properties":{"type":{"type":"string","description":"Type of interaction"},"id":{"type":"string","description":"Unique interaction ID"},"x":{"type":"number","description":"X coordinate"},"y":{"type":"number","description":"Y coordinate"},"link":{"type":"string","description":"Page URL"},"time":{"type":"string","description":"Timestamp"},"bodyHTMLUrl":{"type":"string","description":"URL to captured HTML body"},"screenshotUrl":{"type":"string","description":"URL to captured screenshot"},"target":{"type":"object","properties":{"id":{"type":"string"},"x":{"type":"number"},"y":{"type":"number"},"width":{"type":"number"},"height":{"type":"number"},"tagName":{"type":"string"},"html":{"type":"string"},"innerText":{"type":"string"}},"description":"Target element information"},"key":{"type":"string","description":"Key value"},"code":{"type":"string","description":"Key code"},"metaKeys":{"type":"object","properties":{"alt":{"type":"boolean"},"ctrl":{"type":"boolean"},"meta":{"type":"boolean"},"shift":{"type":"boolean"}},"description":"Modifier keys state"}},"required":["type"],"additionalProperties":true,"title":"WebExtensionInteraction","description":"Web extension interaction in complex format"},"Interaction":{"oneOf":[{"$ref":"#/components/schemas/BrowserInteraction"},{"$ref":"#/components/schemas/WebExtensionInteraction"}],"title":"Interaction","description":"Browser interaction definition. Accepts both simple format (with selector, text, url) and complex format from browser extensions"},"WorkflowFromTemplate":{"type":"object","properties":{"urls":{"type":"array","items":{"type":"string","format":"uri"},"minItems":1,"description":"Source URLs. Multiple URLs must belong to one website: subdomains and country domains of the same name (acme.com, careers.acme.co.uk) count as one website. Requests that span several websites are rejected with 422 SOURCES_MULTIPLE_SITES; create one workflow per website instead, optionally from a shared template."},"name":{"type":"string","minLength":1,"description":"Human-readable name for this workflow (e.g., 'Product Catalog Scraper')"},"description":{"type":"string","maxLength":500,"description":"Detailed description of what this workflow does and why it was created (maximum 500 characters)"},"tags":{"type":"array","items":{"type":"string","minLength":2},"description":"Tags for organizing and categorizing workflows (minimum 2 characters per tag)"},"interval":{"type":"string","enum":["ONLY_ONCE","EVERY_10_MINUTES","EVERY_20_MINUTES","HALF_HOURLY","HOURLY","TWO_HOURLY","THREE_HOURLY","FOUR_HOURLY","SIX_HOURLY","TWELVE_HOURLY","EIGHTEEN_HOURLY","DAILY","TWO_DAY","THREE_DAY","WEEKLY","BIWEEKLY","TRIWEEKLY","FOUR_WEEKS","MONTHLY","CUSTOM"],"description":"How frequently this workflow should run (ONLY_ONCE, HOURLY, DAILY, WEEKLY, etc.)"},"schedules":{"type":"array","items":{"type":"string"},"description":"Cron expressions for custom schedules. Overrides the interval setting for fine-grained control"},"timezone":{"type":"string","description":"IANA timezone for cron `schedules` (e.g. 'America/New_York'). Defaults to UTC. Cron schedules only."},"location":{"$ref":"#/components/schemas/Location"},"bypassPreview":{"default":false,"type":"boolean","description":"Skip preview and validation, deploy scraper immediately. Use with caution - set to true only when you're confident the configuration is correct"},"additionalData":{"nullable":true,"description":"Additional data for the workflow (e.g. IDs from your system to link data)"},"interactions":{"type":"array","items":{"$ref":"#/components/schemas/Interaction"},"description":"Browser interactions to perform before scraping (e.g., clicking buttons, filling forms, scrolling). See Interaction schema for available action types"},"limit":{"type":"integer","minimum":1,"maximum":2147483647,"nullable":true,"description":"Maximum number of items to scrape. Useful for limiting scope during development or cost control. Pass null to clear an existing limit (unlimited)."},"templateId":{"type":"string","format":"uuid","description":"ID of the template to instantiate."},"templateVersion":{"type":"integer","minimum":1,"description":"Optional version (integer) of the template to instantiate. Omit to use the latest published version (resolved once at request time). Provide it to pin a specific version."},"userPrompt":{"type":"string","minLength":10,"maxLength":5000,"description":"Workflow-specific instructions added to the selected template prompt. The template prompt remains template-owned and this text survives template updates."}},"required":["urls","templateId"],"additionalProperties":true,"title":"WorkflowFromTemplate","description":"Create a workflow by instantiating a published template. Only `urls` and `templateId` are required; prompt, schema, frequency, and notifications are inherited from the template version. `templateVersion` is optional — omit it to use the latest published version.\n\nExample: `{\"urls\": [\"https://example.com\"], \"templateId\": \"...\"}`"},"MonitoredField":{"type":"object","properties":{"fieldName":{"type":"string","minLength":1,"description":"Name of the field to monitor"},"operator":{"type":"string","enum":["changed","added","removed"],"description":"Change operator"},"isKeyField":{"type":"boolean","description":"Optional explicit schema-key metadata update for this field. Omit to leave workflow schema key flags unchanged."}},"required":["fieldName","operator"],"title":"MonitoredField","description":"Field monitoring configuration"},"MonitoringConfig":{"description":"Monitoring configuration","type":"object","properties":{"fields":{"type":"array","items":{"$ref":"#/components/schemas/MonitoredField"},"minItems":1,"description":"Fields to monitor (at least one required)"},"channels":{"type":"array","items":{"nullable":true},"description":"Notification channels"},"conditions":{"description":"Condition group with logical operator and conditions"}},"required":["fields"],"title":"MonitoringConfig"},"PromptWorkflow":{"type":"object","properties":{"urls":{"type":"array","items":{"type":"string","format":"uri"},"minItems":1,"description":"Source URLs. Multiple URLs must belong to one website: subdomains and country domains of the same name (acme.com, careers.acme.co.uk) count as one website. Requests that span several websites are rejected with 422 SOURCES_MULTIPLE_SITES; create one workflow per website instead, optionally from a shared template."},"name":{"type":"string","minLength":1,"description":"Human-readable name for this workflow (e.g., 'Product Catalog Scraper')"},"description":{"type":"string","maxLength":500,"description":"Detailed description of what this workflow does and why it was created (maximum 500 characters)"},"tags":{"type":"array","items":{"type":"string","minLength":2},"description":"Tags for organizing and categorizing workflows (minimum 2 characters per tag)"},"limit":{"type":"integer","minimum":1,"maximum":2147483647,"nullable":true,"description":"Maximum number of items to scrape. Useful for limiting scope during development or cost control. Pass null to clear an existing limit (unlimited)."},"location":{"$ref":"#/components/schemas/Location"},"monitoring":{"$ref":"#/components/schemas/MonitoringConfig"},"interval":{"type":"string","enum":["ONLY_ONCE","EVERY_10_MINUTES","EVERY_20_MINUTES","HALF_HOURLY","HOURLY","TWO_HOURLY","THREE_HOURLY","FOUR_HOURLY","SIX_HOURLY","TWELVE_HOURLY","EIGHTEEN_HOURLY","DAILY","TWO_DAY","THREE_DAY","WEEKLY","BIWEEKLY","TRIWEEKLY","FOUR_WEEKS","MONTHLY","CUSTOM"],"description":"How frequently this workflow should run (ONLY_ONCE, HOURLY, DAILY, WEEKLY, etc.)"},"schedules":{"type":"array","items":{"type":"string"},"description":"Cron expressions for custom schedules. Overrides the interval setting for fine-grained control"},"timezone":{"type":"string","description":"IANA timezone for cron `schedules` (e.g. 'America/New_York'). Defaults to UTC. Cron schedules only."},"bypassPreview":{"default":false,"type":"boolean","description":"Skip preview and validation, deploy scraper immediately. Use with caution - set to true only when you're confident the configuration is correct"},"interactions":{"type":"array","items":{"$ref":"#/components/schemas/Interaction"},"description":"Browser interactions to perform before scraping (e.g., clicking buttons, filling forms, scrolling). See Interaction schema for available action types"},"additionalData":{"nullable":true,"description":"Additional data for the workflow (e.g. IDs from your system to link data)"},"templateId":{"type":"string","format":"uuid","description":"Optional: ID of the template this workflow was created from. Records provenance only — the template's config is cloned at creation, not synced."},"templateVersion":{"readOnly":true,"description":"Reserved: only valid in the WorkflowFromTemplate variant. Pairs with templateId to instantiate a specific template version."},"userPrompt":{"type":"string","minLength":10,"maxLength":5000,"description":"Natural language instructions for the workflow (10-5000 characters). Describe what data to extract and how to navigate the site"},"schemaId":{"type":"string","description":"Optional: Schema ID to use with prompt-driven extraction"},"entity":{"type":"string","minLength":1,"description":"Optional: Entity name for prompt-driven extraction"},"fields":{"type":"array","items":{"description":"Extraction field schema","discriminator":{"propertyName":"fieldType"},"oneOf":[{"$ref":"#/components/schemas/DataField"},{"$ref":"#/components/schemas/ClassificationField"}]},"description":"Optional: Additional extraction fields to guide the workflow"}},"required":["urls","userPrompt"],"title":"PromptWorkflow","description":"Create a workflow using natural language instructions to extract data and navigate the site automatically.\n\nExample: `{\"urls\": [\"https://example.com\"], \"userPrompt\": \"Extract all job listings with title, company, salary, and location. Click on each listing to get full details.\"}`"},"WorkflowWithExistingSchema":{"type":"object","properties":{"urls":{"type":"array","items":{"type":"string","format":"uri"},"minItems":1,"description":"Source URLs. Multiple URLs must belong to one website: subdomains and country domains of the same name (acme.com, careers.acme.co.uk) count as one website. Requests that span several websites are rejected with 422 SOURCES_MULTIPLE_SITES; create one workflow per website instead, optionally from a shared template."},"name":{"type":"string","minLength":1,"description":"Human-readable name for this workflow (e.g., 'Product Catalog Scraper')"},"description":{"type":"string","maxLength":500,"description":"Detailed description of what this workflow does and why it was created (maximum 500 characters)"},"tags":{"type":"array","items":{"type":"string","minLength":2},"description":"Tags for organizing and categorizing workflows (minimum 2 characters per tag)"},"limit":{"type":"integer","minimum":1,"maximum":2147483647,"nullable":true,"description":"Maximum number of items to scrape. Useful for limiting scope during development or cost control. Pass null to clear an existing limit (unlimited)."},"location":{"$ref":"#/components/schemas/Location"},"monitoring":{"$ref":"#/components/schemas/MonitoringConfig"},"interval":{"type":"string","enum":["ONLY_ONCE","EVERY_10_MINUTES","EVERY_20_MINUTES","HALF_HOURLY","HOURLY","TWO_HOURLY","THREE_HOURLY","FOUR_HOURLY","SIX_HOURLY","TWELVE_HOURLY","EIGHTEEN_HOURLY","DAILY","TWO_DAY","THREE_DAY","WEEKLY","BIWEEKLY","TRIWEEKLY","FOUR_WEEKS","MONTHLY","CUSTOM"],"description":"How frequently this workflow should run (ONLY_ONCE, HOURLY, DAILY, WEEKLY, etc.)"},"schedules":{"type":"array","items":{"type":"string"},"description":"Cron expressions for custom schedules. Overrides the interval setting for fine-grained control"},"timezone":{"type":"string","description":"IANA timezone for cron `schedules` (e.g. 'America/New_York'). Defaults to UTC. Cron schedules only."},"bypassPreview":{"default":false,"type":"boolean","description":"Skip preview and validation, deploy scraper immediately. Use with caution - set to true only when you're confident the configuration is correct"},"interactions":{"type":"array","items":{"$ref":"#/components/schemas/Interaction"},"description":"Browser interactions to perform before scraping (e.g., clicking buttons, filling forms, scrolling). See Interaction schema for available action types"},"additionalData":{"nullable":true,"description":"Additional data for the workflow (e.g. IDs from your system to link data)"},"templateId":{"type":"string","format":"uuid","description":"Optional: ID of the template this workflow was created from. Records provenance only — the template's config is cloned at creation, not synced."},"templateVersion":{"readOnly":true,"description":"Reserved: only valid in the WorkflowFromTemplate variant. Pairs with templateId to instantiate a specific template version."},"schemaId":{"type":"string","description":"ID of an existing schema configuration. Use this to reference a previously defined schema without re-defining extraction fields"}},"required":["urls","schemaId"],"title":"WorkflowWithExistingSchema","description":"Create a workflow using a pre-defined schema configuration. Reference an existing schema by ID to extract data without re-defining fields. Perfect when you have multiple workflows using the same data structure.\n\nExample: `{\"urls\": [\"https://example.com\"], \"schemaId\": \"schema-abc123\", \"interval\": \"DAILY\"}`"},"WorkflowWithEntityAndFields":{"type":"object","properties":{"urls":{"type":"array","items":{"type":"string","format":"uri"},"minItems":1,"description":"Source URLs. Multiple URLs must belong to one website: subdomains and country domains of the same name (acme.com, careers.acme.co.uk) count as one website. Requests that span several websites are rejected with 422 SOURCES_MULTIPLE_SITES; create one workflow per website instead, optionally from a shared template."},"name":{"type":"string","minLength":1,"description":"Human-readable name for this workflow (e.g., 'Product Catalog Scraper')"},"description":{"type":"string","maxLength":500,"description":"Detailed description of what this workflow does and why it was created (maximum 500 characters)"},"tags":{"type":"array","items":{"type":"string","minLength":2},"description":"Tags for organizing and categorizing workflows (minimum 2 characters per tag)"},"limit":{"type":"integer","minimum":1,"maximum":2147483647,"nullable":true,"description":"Maximum number of items to scrape. Useful for limiting scope during development or cost control. Pass null to clear an existing limit (unlimited)."},"location":{"$ref":"#/components/schemas/Location"},"monitoring":{"$ref":"#/components/schemas/MonitoringConfig"},"interval":{"type":"string","enum":["ONLY_ONCE","EVERY_10_MINUTES","EVERY_20_MINUTES","HALF_HOURLY","HOURLY","TWO_HOURLY","THREE_HOURLY","FOUR_HOURLY","SIX_HOURLY","TWELVE_HOURLY","EIGHTEEN_HOURLY","DAILY","TWO_DAY","THREE_DAY","WEEKLY","BIWEEKLY","TRIWEEKLY","FOUR_WEEKS","MONTHLY","CUSTOM"],"description":"How frequently this workflow should run (ONLY_ONCE, HOURLY, DAILY, WEEKLY, etc.)"},"schedules":{"type":"array","items":{"type":"string"},"description":"Cron expressions for custom schedules. Overrides the interval setting for fine-grained control"},"timezone":{"type":"string","description":"IANA timezone for cron `schedules` (e.g. 'America/New_York'). Defaults to UTC. Cron schedules only."},"bypassPreview":{"default":false,"type":"boolean","description":"Skip preview and validation, deploy scraper immediately. Use with caution - set to true only when you're confident the configuration is correct"},"interactions":{"type":"array","items":{"$ref":"#/components/schemas/Interaction"},"description":"Browser interactions to perform before scraping (e.g., clicking buttons, filling forms, scrolling). See Interaction schema for available action types"},"additionalData":{"nullable":true,"description":"Additional data for the workflow (e.g. IDs from your system to link data)"},"templateId":{"type":"string","format":"uuid","description":"Optional: ID of the template this workflow was created from. Records provenance only — the template's config is cloned at creation, not synced."},"templateVersion":{"readOnly":true,"description":"Reserved: only valid in the WorkflowFromTemplate variant. Pairs with templateId to instantiate a specific template version."},"entity":{"type":"string","minLength":1,"description":"Entity name for extraction (e.g., 'Product', 'JobListing')"},"fields":{"type":"array","items":{"description":"Extraction field schema","discriminator":{"propertyName":"fieldType"},"oneOf":[{"$ref":"#/components/schemas/DataField"},{"$ref":"#/components/schemas/ClassificationField"}]},"minItems":1,"description":"Array of fields to extract from each item. Each field defines a property to capture (e.g., title, price, description)"}},"required":["urls","entity","fields"],"title":"WorkflowWithEntityAndFields","description":"Create a workflow by defining extraction entity and fields directly in the request. Inline your schema definition to quickly set up custom data extraction without creating a schema separately.\n\nExample: `{\"urls\": [\"https://example.com\"], \"entity\": \"Product\", \"fields\": [{\"name\": \"title\", \"description\": \"Product title\", \"fieldType\": \"SCHEMA\", \"dataType\": \"STRING\"}, {\"name\": \"price\", \"description\": \"Product price\", \"fieldType\": \"SCHEMA\", \"dataType\": \"NUMBER\"}]}`"},"CreateWorkflowBody":{"title":"CreateWorkflowBody","description":"Request body for creating a new workflow","anyOf":[{"$ref":"#/components/schemas/WorkflowFromTemplate"},{"$ref":"#/components/schemas/PromptWorkflow"},{"$ref":"#/components/schemas/WorkflowWithExistingSchema"},{"$ref":"#/components/schemas/WorkflowWithEntityAndFields"}]},"CreateWorkflowResponse":{"type":"object","properties":{"error":{"type":"boolean","enum":[false],"description":"Error flag (always false on success)"},"success":{"type":"boolean","description":"Success flag"},"workflowId":{"type":"string","description":"ID of the created workflow"},"message":{"type":"string","description":"Success message"}},"required":["error","success","workflowId","message"],"title":"CreateWorkflowResponse","description":"Response for workflow creation"},"TemplateControlledFieldError":{"type":"object","properties":{"error":{"type":"boolean","enum":[true],"description":"Error flag"},"code":{"type":"string","enum":["TEMPLATE_CONTROLLED_FIELD"],"description":"Stable error code"},"message":{"type":"string","description":"Human-readable error message"},"templateId":{"type":"string","format":"uuid","description":"Template that controls the offending fields"},"fields":{"type":"array","items":{"type":"string"},"description":"Controlled field names the caller tried to override"}},"required":["error","code","message","templateId","fields"],"title":"TemplateControlledFieldError"},"SourcesMultipleSitesError":{"type":"object","properties":{"error":{"type":"boolean","enum":[true],"description":"Error flag"},"code":{"type":"string","enum":["SOURCES_MULTIPLE_SITES"],"description":"Stable error code"},"message":{"type":"string","description":"What to do instead: one workflow per website, optionally from a template"},"details":{"type":"object","properties":{"sites":{"type":"array","items":{"type":"object","properties":{"site":{"type":"string","description":"Website the URLs belong to, e.g. acme.com"},"urls":{"type":"array","items":{"type":"string"},"description":"Requested URLs on this website"}},"required":["site","urls"]},"description":"Requested URLs grouped by website"},"newSites":{"type":"array","items":{"type":"string"},"description":"Websites the request adds to the workflow (all of them on create)"},"currentSites":{"type":"array","items":{"type":"string"},"description":"Websites the workflow already covers (empty on create)"}},"required":["sites","newSites","currentSites"]}},"required":["error","code","message","details"],"title":"SourcesMultipleSitesError","description":"The source URLs span several websites. A workflow covers one website."},"JobError":{"type":"object","properties":{"errorCode":{"type":"string","description":"Error code identifying the type of error"},"message":{"type":"string","description":"Human-readable error message"},"occurredAt":{"type":"string","format":"date-time","description":"Timestamp when the error occurred"},"screenshot":{"type":"string","description":"URL to error screenshot if available"},"context":{"type":"object","additionalProperties":{"nullable":true},"description":"Additional error context"}},"required":["errorCode","message","occurredAt"],"title":"JobError","description":"Error information for a job"},"JobStatusSnapshotBlock":{"type":"object","properties":{"configHash":{"type":"string","description":"sha256 of the canonical config the run was executed against"},"snapshotCreatedAt":{"type":"string","format":"date-time","description":"When the snapshot draft was inserted (run entry)"},"snapshotConfirmedAt":{"type":"string","format":"date-time","description":"When the snapshot was confirmed (terminal success); null while draft","nullable":true},"isConfigStaleVsCurrent":{"type":"boolean","description":"True when the snapshot hash differs from the workflow's current canonical hash"},"driftKeys":{"type":"array","items":{"type":"string"},"description":"Top-level config keys that differ from the current config"},"runBuildId":{"type":"string","description":"Shelly build that produced this run; null for legacy rows and non-SHELLY_SCRIPT workflows","nullable":true},"currentBuildId":{"type":"string","description":"The workflow's live Shelly build, or null when none has gone live","nullable":true},"isBuildStaleVsCurrent":{"type":"boolean","description":"True when runBuildId is set and differs from currentBuildId — the script that produced this run's data is no longer the one the workflow runs"},"workspaceClean":{"type":"boolean","description":"True when the live Shelly workspace matches the latest completed build input; null when unknown","nullable":true},"freshnessReason":{"type":"string","enum":["config_drift","build_drift","workspace_dirty","no_build_yet"],"description":"Priority freshness reason for the snapshot block; null when config, build, and workspace are fresh","nullable":true}},"required":["configHash","snapshotCreatedAt","snapshotConfirmedAt","isConfigStaleVsCurrent","driftKeys","runBuildId","currentBuildId","isBuildStaleVsCurrent","workspaceClean","freshnessReason"],"title":"JobStatusSnapshotBlock","description":"ADR-009 snapshot drift block; null for runs predating the snapshot migration"},"JobStatusResponse":{"type":"object","properties":{"id":{"type":"string","description":"The job ID"},"state":{"type":"string","enum":["IN_PROGRESS","FINISHED","FAILED","NOT_SUPPORTED","FAILED_INSUFFICIENT_FUNDS"],"description":"Current state of the job"},"startedAt":{"type":"string","format":"date-time","description":"Start date and time of the job"},"finishedAt":{"type":"string","format":"date-time","description":"Finish date and time of the job (if completed)"},"estimatedFinishedAtUtc":{"type":"string","format":"date-time","nullable":true,"description":"Estimated UTC finish time for an active workflow run"},"limit":{"type":"integer","nullable":true,"description":"Record limit for the job"},"workflowId":{"type":"string","description":"ID of the workflow/scraper"},"variables":{"type":"object","additionalProperties":{"nullable":true},"description":"Job variables"},"errors":{"type":"array","items":{"$ref":"#/components/schemas/JobError"},"description":"List of errors if the job failed"},"snapshot":{"nullable":true,"allOf":[{"$ref":"#/components/schemas/JobStatusSnapshotBlock"}]}},"required":["id","state"],"title":"JobStatusResponse","description":"Job status and telemetry response"},"JobStatusErrorResponse":{"type":"object","properties":{"error":{"type":"string","description":"Error message"}},"required":["error"],"title":"JobStatusErrorResponse","description":"Error response for job status endpoint"},"ActivityEventSource":{"type":"object","properties":{"requestSource":{"type":"string","description":"Request source that triggered the event (SYSTEM, UI, SDK, API)"},"userId":{"type":"string","description":"User ID who triggered the event"},"userEmail":{"type":"string","description":"User email who triggered the event"}},"title":"ActivityEventSource","description":"Source information for an activity event"},"ActivityEventResource":{"type":"object","properties":{"type":{"type":"string","description":"Resource type (RUN, WORKFLOW, NOTIFICATION, etc.)"},"workflowId":{"type":"string","description":"Associated workflow ID"},"resourceId":{"type":"string","description":"Resource identifier"},"name":{"type":"string","description":"Resource name"}},"required":["type"],"title":"ActivityEventResource","description":"Resource information for an activity event"},"ActivityEventDetails":{"type":"object","additionalProperties":{"nullable":true},"title":"ActivityEventDetails","description":"Additional details about the activity event (varies by event type)"},"ActivityEvent":{"type":"object","properties":{"title":{"type":"string","description":"Event title/type"},"dateTime":{"type":"string","format":"date-time","description":"ISO 8601 timestamp of the event"},"source":{"$ref":"#/components/schemas/ActivityEventSource"},"resource":{"$ref":"#/components/schemas/ActivityEventResource"},"details":{"$ref":"#/components/schemas/ActivityEventDetails"}},"required":["title","dateTime"],"title":"ActivityEvent","description":"A single activity event"},"ActivityPaginationMeta":{"type":"object","properties":{"total":{"type":"integer","minimum":0,"description":"Total number of events"},"limit":{"type":"integer","minimum":1,"description":"Number of events per page"},"offset":{"type":"integer","minimum":0,"description":"Offset for pagination"},"hasMore":{"type":"boolean","description":"Whether there are more events available"}},"required":["total","limit","offset","hasMore"],"title":"ActivityPaginationMeta","description":"Pagination metadata for activity events"},"ActivityListResponse":{"type":"object","properties":{"error":{"type":"boolean","enum":[false]},"data":{"type":"object","properties":{"events":{"type":"array","items":{"$ref":"#/components/schemas/ActivityEvent"}},"pagination":{"$ref":"#/components/schemas/ActivityPaginationMeta"}},"required":["events","pagination"]}},"required":["error","data"],"title":"ActivityListResponse","description":"Successful response containing activity events and pagination"},"CreateVariableBody":{"oneOf":[{"type":"object","properties":{"key":{"type":"string","minLength":1,"description":"Variable key (must be unique within scope)"},"value":{"type":"string","description":"Variable value"},"dataType":{"type":"string","enum":["STRING","OBJECT","ARRAY","NUMBER"]}},"required":["key","value"]},{"type":"object","properties":{"key":{"type":"string","minLength":1,"description":"Secret key (must be unique within team scope)"},"value":{"type":"string","minLength":1,"description":"Write-only secret value"},"dataType":{"type":"string","enum":["SECRET"]},"managementMode":{"type":"string","enum":["KADOA_MANAGED"]}},"required":["key","value","dataType"]},{"type":"object","properties":{"key":{"type":"string","minLength":1,"description":"Secret key (must be unique within team scope)"},"dataType":{"type":"string","enum":["SECRET"]},"managementMode":{"type":"string","enum":["CUSTOMER_MANAGED"]},"providerConnectionId":{"type":"string","format":"uuid"},"resourceReference":{"type":"string","minLength":1}},"required":["key","dataType","managementMode","providerConnectionId","resourceReference"]}],"title":"CreateVariableBody","description":"Request body for creating a variable or write-only secret"},"Variable":{"oneOf":[{"type":"object","properties":{"id":{"type":"string","description":"Unique variable identifier"},"key":{"type":"string","description":"Variable key (unique per team/user scope)"},"value":{"type":"string","description":"Variable value"},"dataType":{"type":"string","enum":["STRING","OBJECT","ARRAY","NUMBER"]},"createdAt":{"type":"string","description":"ISO 8601 creation timestamp"},"updatedAt":{"type":"string","description":"ISO 8601 last update timestamp"}},"required":["id","key","value","createdAt"]},{"type":"object","properties":{"id":{"type":"string","description":"Unique variable identifier"},"key":{"type":"string","description":"Variable key (unique per team scope)"},"dataType":{"type":"string","enum":["SECRET"]},"provider":{"type":"string","enum":["GOOGLE_SECRET_MANAGER"]},"managementMode":{"type":"string","enum":["KADOA_MANAGED","CUSTOMER_MANAGED"]},"status":{"type":"string","enum":["ACTIVE","NEEDS_ATTENTION","DELETING"]},"currentVersion":{"type":"string"},"lastResolvedVersion":{"type":"string"},"createdAt":{"type":"string","description":"ISO 8601 creation timestamp"},"updatedAt":{"type":"string","description":"ISO 8601 last update timestamp"},"lastRotatedAt":{"type":"string"},"lastResolvedAt":{"type":"string"}},"required":["id","key","dataType","provider","managementMode","status","createdAt"]}],"title":"Variable","description":"A variable. Secret responses contain metadata only and never expose the value."},"VariableResponse":{"type":"object","properties":{"variable":{"nullable":true,"allOf":[{"$ref":"#/components/schemas/Variable"}]},"error":{"type":"string","nullable":true}},"required":["variable","error"],"title":"VariableResponse","description":"Response containing a single variable"},"VariablesListResponse":{"type":"object","properties":{"variables":{"type":"array","items":{"$ref":"#/components/schemas/Variable"}},"error":{"type":"string","nullable":true}},"required":["variables","error"],"title":"VariablesListResponse","description":"Response containing a list of variables"},"VariableDataType":{"default":"STRING","type":"string","enum":["STRING","SECRET","OBJECT","ARRAY","NUMBER"],"title":"VariableDataType","description":"The data type of the variable value"},"UpdateVariableBody":{"type":"object","properties":{"key":{"type":"string","minLength":1,"description":"Variable key (must be unique within scope)"},"value":{"type":"string","description":"New variable value or write-only secret value"},"dataType":{"$ref":"#/components/schemas/VariableDataType"}},"title":"UpdateVariableBody","description":"Request body for updating a variable. Variable type cannot be changed."}},"securitySchemes":{"ApiKeyAuth":{"type":"apiKey","in":"header","name":"x-api-key","description":"API key for authentication"},"BearerAuth":{"type":"http","scheme":"bearer","bearerFormat":"JWT","description":"Bearer token for authentication"}}}}