{"servers":[{"url":"/api/v1","description":"Same-origin (current environment)"},{"url":"https://app.contracko.com/api/v1","description":"Production"}],"info":{"title":"Contracko Parsing API","version":"0.1.0","description":"Programmatic contract parsing with API key authentication and structured JSON, CSV, and Excel outputs."},"security":[{"ContrackoApiKey":[]},{"BearerAuth":[]}],"tags":[{"name":"Authentication","description":"Verify and inspect Contracko integration API keys.\n\nSend your API key in `x-contracko-api-key` or `Authorization: Bearer <key>`. Use `GET /health` to confirm the key is valid and discover the granted scopes."},{"name":"Parsing API","description":"Contracko Parser: separate bulk document processing using Parser credits, not needed to add contracts to your contract register. Without an eligible Parser subscription, the workspace gets a one-time allowance of 20 free Parser credits, not 20 guaranteed extractions. Extraction costs 1–5 credits per document; review doubles that cost. After the free allowance, paid Parser credits are needed.\n\n**Authentication:** API key with the `parser:compute` scope."},{"name":"Contract Types","description":"Discover and manage contract types that can be referenced when ingesting contracts or queueing parser jobs with an explicit `categoryId`.\n\n**Authentication:** API key with `contract:read` for read endpoints, `contract:write` for write endpoints, or `parser:compute` for all contract-type endpoints.\n\nContract scopes require Contract Management API access. The `parser:compute` scope requires Parsing API access. Create, update, and delete also require the issuing user to retain contract-type management permission."}],"components":{"securitySchemes":{"ContrackoApiKey":{"type":"apiKey","in":"header","name":"x-contracko-api-key","description":"Contracko integration API key. Issue keys from Settings → Integrations → API keys."},"BearerAuth":{"type":"http","scheme":"bearer","bearerFormat":"opaque","description":"Pass your Contracko integration API key as a bearer token: `Authorization: Bearer <key>`."}},"schemas":{"ApiError":{"type":"object","required":["code","message"],"properties":{"code":{"type":"string","description":"Machine-readable ORPC/TRPC error code."},"message":{"type":"string","description":"Human-readable error message."},"data":{"type":"object","description":"Optional structured metadata with endpoint-specific error context.","properties":{"refusalReason":{"type":"string","enum":["subscription_inactive","api_disabled","not_member"],"description":"Reviewed Contract Management or membership refusal reason."}},"additionalProperties":true}},"additionalProperties":true}}},"openapi":"3.1.1","paths":{"/health":{"get":{"operationId":"health","summary":"Check API key access","description":"Verify that your API key is valid and return the workspace and access attached to it.","tags":["Authentication"],"responses":{"200":{"description":"API key verified.","content":{"application/json":{"schema":{"type":"object","properties":{"status":{"const":"ok","description":"Health status for the authenticated API key"},"timestamp":{"type":"string","format":"date-time","description":"ISO-8601 timestamp generated by the API"},"keyId":{"type":"string","minLength":1,"description":"Unique identifier for the API key"},"keyName":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Label assigned to the API key"},"scopes":{"type":"array","items":{"type":"string","minLength":1},"description":"Access granted to the API key"},"workspace":{"type":"object","properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Connected workspace name"},"contractManagement":{"type":"object","properties":{"refusalReason":{"enum":["subscription_inactive","api_disabled","not_member"],"type":"string"},"hint":{"type":"string"}},"required":["refusalReason","hint"],"description":"Bounded Contract Management refusal and recovery hint; the credential remains valid"},"contracts":{"type":"object","properties":{"real":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"Contracts added by the workspace"},"examples":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"Example contracts seeded for onboarding, titled \"Example: ...\""}},"required":["real","examples"],"description":"Visible contract counts; present only with contract read access"}},"required":["name"],"description":"Connected workspace summary, returned to MCP connections only"}},"required":["status","timestamp","keyId","scopes"]},"examples":{"success":{"summary":"API key verified","value":{"status":"ok","timestamp":"2026-03-13T10:30:00.000Z","keyId":"key_123","keyName":"Production parser key","scopes":["parser:compute"]}}}}}},"401":{"description":"Authentication failed (missing, invalid, revoked, or expired API key).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"missing_api_key":{"summary":"No API key header provided","value":{"code":"UNAUTHORIZED","message":"Missing API key. Send x-contracko-api-key or Authorization: Bearer <key>."}}}}}},"429":{"description":"Retry later because the request rate limit was reached.","headers":{"Retry-After":{"description":"Number of seconds to wait before retrying the request.","schema":{"type":"string"}},"X-RateLimit-Limit":{"description":"Requests allowed in the current rate-limit window.","schema":{"type":"string"}},"X-RateLimit-Remaining":{"description":"Remaining requests in the current rate-limit window.","schema":{"type":"string"}},"X-RateLimit-Reset":{"description":"Unix timestamp when the current rate-limit window resets.","schema":{"type":"string"}}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"rate_limited":{"summary":"API rate limit reached","value":{"code":"TOO_MANY_REQUESTS","message":"Too many requests. Please try again later."}}}}}},"500":{"description":"The server could not complete the request.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"internal_error":{"summary":"Unhandled server error","value":{"code":"INTERNAL_SERVER_ERROR","message":"Unexpected API error"}}}}}}}}},"/contract-types":{"get":{"operationId":"contractTypes.list","summary":"List contract types","description":"Returns contract types scoped to the API key organisation. Use these types for contract intake or as parser extraction schemas referenced by categoryId.","tags":["Contract Types"],"parameters":[{"name":"limit","in":"query","schema":{"type":"integer","minimum":1,"maximum":100},"allowEmptyValue":true,"allowReserved":true},{"name":"cursor","in":"query","schema":{"type":"string","minLength":1},"allowEmptyValue":true,"allowReserved":true}],"responses":{"200":{"description":"Contract types returned.","content":{"application/json":{"schema":{"type":"object","properties":{"items":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"name":{"type":"string"},"description":{"anyOf":[{"type":"string"},{"type":"null"}]},"organisationId":{"type":"string"},"isDefault":{"type":"boolean"},"source":{"enum":["manual","template_adoption","starting_template","ai_generated"],"type":"string"},"sourceTemplateId":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}]},"sourceTemplateSlug":{"anyOf":[{"type":"string"},{"type":"null"}]},"entityStatus":{"anyOf":[{"enum":["pending-review","archived"],"type":"string"},{"type":"null"}],"description":"Read-only review state. AI-created types can be pending-review; any update clears it to null."},"createdAt":{"type":"string","format":"date-time","x-native-type":"date"},"updatedAt":{"type":"string","format":"date-time","x-native-type":"date"},"fields":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"name":{"type":"string"},"fieldKey":{"type":"string"},"description":{"anyOf":[{"type":"string"},{"type":"null"}]},"placeholder":{"anyOf":[{"type":"string"},{"type":"null"}]},"fieldType":{"enum":["text","number","date","boolean","currency","percentage","select","multi_select"],"type":"string"},"required":{"type":"boolean"},"config":{"anyOf":[{"anyOf":[{"type":"string"},{"type":"number"},{"type":"boolean"},{"type":"null"}]},{"type":"object","propertyNames":{"type":"string"},"additionalProperties":{}},{"type":"array","items":{"anyOf":[{},{"type":"null"}]}}]},"defaultValue":{"anyOf":[{"anyOf":[{"anyOf":[{"type":"string"},{"type":"number"},{"type":"boolean"},{"type":"null"}]},{"type":"object","propertyNames":{"type":"string"},"additionalProperties":{}},{"type":"array","items":{"anyOf":[{},{"type":"null"}]}}]},{"type":"null"}]},"displayOrder":{"type":"integer","minimum":-2147483648,"maximum":2147483647},"categoryId":{"type":"string","format":"uuid"},"createdAt":{"type":"string","format":"date-time","x-native-type":"date"},"updatedAt":{"type":"string","format":"date-time","x-native-type":"date"}},"required":["id","name","fieldKey","description","placeholder","fieldType","required","config","defaultValue","displayOrder","categoryId","createdAt","updatedAt"]},"description":"Custom fields of this contract type"}},"required":["id","name","description","organisationId","isDefault","source","sourceTemplateId","sourceTemplateSlug","entityStatus","createdAt","updatedAt","fields"]},"description":"Contract types in this workspace"},"nextCursor":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Present only on paginated lists; null at the end."}},"required":["items"]},"examples":{"success":{"summary":"Contract types returned","value":{"items":[{"id":"550e8400-e29b-41d4-a716-446655440000","name":"Master Services Agreement","description":"Commercial services agreements","organisationId":"org_123","isDefault":false,"source":"manual","sourceTemplateId":null,"sourceTemplateSlug":null,"entityStatus":null,"fields":[],"createdAt":"2026-02-18T10:30:00.000Z","updatedAt":"2026-02-18T10:30:00.000Z"}]}}}}}},"401":{"description":"Authentication failed (missing, invalid, revoked, or expired API key).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"missing_api_key":{"summary":"No API key header provided","value":{"code":"UNAUTHORIZED","message":"Missing API key. Send x-contracko-api-key or Authorization: Bearer <key>."}}}}}},"403":{"description":"Access denied because the API key does not include the required access for this operation.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"missing_scope":{"summary":"API key does not have access","value":{"code":"FORBIDDEN","message":"This API key does not have access to this endpoint.","data":{"requiredScopes":["required:scope"],"availableScopes":["resource:read"]}}}}}}},"429":{"description":"Retry later because the request rate limit was reached.","headers":{"Retry-After":{"description":"Number of seconds to wait before retrying the request.","schema":{"type":"string"}},"X-RateLimit-Limit":{"description":"Requests allowed in the current rate-limit window.","schema":{"type":"string"}},"X-RateLimit-Remaining":{"description":"Remaining requests in the current rate-limit window.","schema":{"type":"string"}},"X-RateLimit-Reset":{"description":"Unix timestamp when the current rate-limit window resets.","schema":{"type":"string"}}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"rate_limited":{"summary":"API rate limit reached","value":{"code":"TOO_MANY_REQUESTS","message":"Too many requests. Please try again later."}}}}}},"500":{"description":"The server could not complete the request.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"internal_error":{"summary":"Unhandled server error","value":{"code":"INTERNAL_SERVER_ERROR","message":"Unexpected API error"}}}}}}}},"post":{"operationId":"contractTypes.create","summary":"Create a contract type","description":"Creates a contract type, optionally with custom fields, in the API key organisation.","tags":["Contract Types"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"name":{"type":"string","description":"Contract type name"},"description":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"description":"Optional description"},"fields":{"type":"array","items":{"type":"object","properties":{"name":{"type":"string"},"fieldKey":{"type":"string","pattern":"^[a-z0-9_]+$"},"description":{"type":"string"},"placeholder":{"type":"string"},"fieldType":{"enum":["text","number","date","boolean","currency","percentage","select","multi_select"],"type":"string"},"required":{"type":"boolean","default":false},"config":{"type":"object","propertyNames":{"type":"string"},"additionalProperties":{"anyOf":[{"anyOf":[{"type":"string"},{"type":"number"},{"type":"boolean"},{"type":"null"}]},{"type":"array","items":{"anyOf":[{"anyOf":[{"type":"string"},{"type":"number"},{"type":"boolean"},{"type":"null"}]},{"type":"array","items":{}},{"type":"object","propertyNames":{"type":"string"},"additionalProperties":{}}]}},{"type":"object","propertyNames":{"type":"string"},"additionalProperties":{"anyOf":[{"anyOf":[{"type":"string"},{"type":"number"},{"type":"boolean"},{"type":"null"}]},{"type":"array","items":{}},{"type":"object","propertyNames":{"type":"string"},"additionalProperties":{}}]}}]},"default":{},"description":"Type-specific settings: select and multi_select need options (string array); number may set min, max and decimalPlaces."},"options":{"type":"array","items":{"type":"string"}},"defaultValue":{"anyOf":[{"anyOf":[{"type":"string"},{"type":"number"},{"type":"boolean"},{"type":"null"}]},{"type":"array","items":{"anyOf":[{"anyOf":[{"type":"string"},{"type":"number"},{"type":"boolean"},{"type":"null"}]},{"type":"array","items":{}},{"type":"object","propertyNames":{"type":"string"},"additionalProperties":{}}]}},{"type":"object","propertyNames":{"type":"string"},"additionalProperties":{"anyOf":[{"anyOf":[{"type":"string"},{"type":"number"},{"type":"boolean"},{"type":"null"}]},{"type":"array","items":{}},{"type":"object","propertyNames":{"type":"string"},"additionalProperties":{}}]}}]}},"required":["name","fieldKey","fieldType"]},"default":[],"description":"Optional custom fields to create with the contract type"}},"required":["name"],"additionalProperties":false,"description":"Input payload for creating a contract type."}}}},"responses":{"200":{"description":"Contract type created.","content":{"application/json":{"schema":{"type":"object","properties":{"contractType":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"name":{"type":"string"},"description":{"anyOf":[{"type":"string"},{"type":"null"}]},"organisationId":{"type":"string"},"isDefault":{"type":"boolean"},"source":{"enum":["manual","template_adoption","starting_template","ai_generated"],"type":"string"},"sourceTemplateId":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}]},"sourceTemplateSlug":{"anyOf":[{"type":"string"},{"type":"null"}]},"entityStatus":{"anyOf":[{"enum":["pending-review","archived"],"type":"string"},{"type":"null"}],"description":"Read-only review state. AI-created types can be pending-review; any update clears it to null."},"createdAt":{"type":"string","format":"date-time","x-native-type":"date"},"updatedAt":{"type":"string","format":"date-time","x-native-type":"date"},"fields":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"name":{"type":"string"},"fieldKey":{"type":"string"},"description":{"anyOf":[{"type":"string"},{"type":"null"}]},"placeholder":{"anyOf":[{"type":"string"},{"type":"null"}]},"fieldType":{"enum":["text","number","date","boolean","currency","percentage","select","multi_select"],"type":"string"},"required":{"type":"boolean"},"config":{"anyOf":[{"anyOf":[{"type":"string"},{"type":"number"},{"type":"boolean"},{"type":"null"}]},{"type":"object","propertyNames":{"type":"string"},"additionalProperties":{}},{"type":"array","items":{"anyOf":[{},{"type":"null"}]}}]},"defaultValue":{"anyOf":[{"anyOf":[{"anyOf":[{"type":"string"},{"type":"number"},{"type":"boolean"},{"type":"null"}]},{"type":"object","propertyNames":{"type":"string"},"additionalProperties":{}},{"type":"array","items":{"anyOf":[{},{"type":"null"}]}}]},{"type":"null"}]},"displayOrder":{"type":"integer","minimum":-2147483648,"maximum":2147483647},"categoryId":{"type":"string","format":"uuid"},"createdAt":{"type":"string","format":"date-time","x-native-type":"date"},"updatedAt":{"type":"string","format":"date-time","x-native-type":"date"}},"required":["id","name","fieldKey","description","placeholder","fieldType","required","config","defaultValue","displayOrder","categoryId","createdAt","updatedAt"]},"description":"Custom fields of this contract type"}},"required":["id","name","description","organisationId","isDefault","source","sourceTemplateId","sourceTemplateSlug","entityStatus","createdAt","updatedAt","fields"],"description":"Contract type stored in Contracko"}},"required":["contractType"]}}}},"400":{"description":"Request validation failed (payload, query, or path format is invalid).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"validation_failed":{"summary":"Invalid input payload","value":{"code":"BAD_REQUEST","message":"Request validation failed","data":{"issues":[{"path":["files",0,"mimeType"],"message":"Invalid MIME type."}]}}}}}}},"401":{"description":"Authentication failed (missing, invalid, revoked, or expired API key).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"missing_api_key":{"summary":"No API key header provided","value":{"code":"UNAUTHORIZED","message":"Missing API key. Send x-contracko-api-key or Authorization: Bearer <key>."}}}}}},"403":{"description":"Access denied because the API key does not include the required access for this operation.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"missing_scope":{"summary":"API key does not have access","value":{"code":"FORBIDDEN","message":"This API key does not have access to this endpoint.","data":{"requiredScopes":["required:scope"],"availableScopes":["resource:read"]}}}}}}},"409":{"description":"A previous request with the same idempotency key is still being processed.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"idempotency_conflict":{"summary":"Idempotency key already processing","value":{"code":"CONFLICT","message":"Idempotency-Key is already being processed. Retry shortly."}}}}}},"422":{"description":"Request is well-formed but contains values the API cannot process.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"semantic_validation_failed":{"summary":"Request values are incompatible","value":{"code":"UNPROCESSABLE_CONTENT","message":"Request contains values that cannot be processed."}}}}}},"429":{"description":"Retry later because the request rate limit was reached.","headers":{"Retry-After":{"description":"Number of seconds to wait before retrying the request.","schema":{"type":"string"}},"X-RateLimit-Limit":{"description":"Requests allowed in the current rate-limit window.","schema":{"type":"string"}},"X-RateLimit-Remaining":{"description":"Remaining requests in the current rate-limit window.","schema":{"type":"string"}},"X-RateLimit-Reset":{"description":"Unix timestamp when the current rate-limit window resets.","schema":{"type":"string"}}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"rate_limited":{"summary":"API rate limit reached","value":{"code":"TOO_MANY_REQUESTS","message":"Too many requests. Please try again later."}}}}}},"500":{"description":"The server could not complete the request.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"internal_error":{"summary":"Unhandled server error","value":{"code":"INTERNAL_SERVER_ERROR","message":"Unexpected API error"}}}}}}}}},"/contract-types/{id}":{"get":{"operationId":"contractTypes.get","summary":"Get a contract type","description":"Returns a single contract type scoped to the API key organisation.","tags":["Contract Types"],"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Contract type UUID"}}],"responses":{"200":{"description":"Contract type returned.","content":{"application/json":{"schema":{"type":"object","properties":{"contractType":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"name":{"type":"string"},"description":{"anyOf":[{"type":"string"},{"type":"null"}]},"organisationId":{"type":"string"},"isDefault":{"type":"boolean"},"source":{"enum":["manual","template_adoption","starting_template","ai_generated"],"type":"string"},"sourceTemplateId":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}]},"sourceTemplateSlug":{"anyOf":[{"type":"string"},{"type":"null"}]},"entityStatus":{"anyOf":[{"enum":["pending-review","archived"],"type":"string"},{"type":"null"}],"description":"Read-only review state. AI-created types can be pending-review; any update clears it to null."},"createdAt":{"type":"string","format":"date-time","x-native-type":"date"},"updatedAt":{"type":"string","format":"date-time","x-native-type":"date"},"fields":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"name":{"type":"string"},"fieldKey":{"type":"string"},"description":{"anyOf":[{"type":"string"},{"type":"null"}]},"placeholder":{"anyOf":[{"type":"string"},{"type":"null"}]},"fieldType":{"enum":["text","number","date","boolean","currency","percentage","select","multi_select"],"type":"string"},"required":{"type":"boolean"},"config":{"anyOf":[{"anyOf":[{"type":"string"},{"type":"number"},{"type":"boolean"},{"type":"null"}]},{"type":"object","propertyNames":{"type":"string"},"additionalProperties":{}},{"type":"array","items":{"anyOf":[{},{"type":"null"}]}}]},"defaultValue":{"anyOf":[{"anyOf":[{"anyOf":[{"type":"string"},{"type":"number"},{"type":"boolean"},{"type":"null"}]},{"type":"object","propertyNames":{"type":"string"},"additionalProperties":{}},{"type":"array","items":{"anyOf":[{},{"type":"null"}]}}]},{"type":"null"}]},"displayOrder":{"type":"integer","minimum":-2147483648,"maximum":2147483647},"categoryId":{"type":"string","format":"uuid"},"createdAt":{"type":"string","format":"date-time","x-native-type":"date"},"updatedAt":{"type":"string","format":"date-time","x-native-type":"date"}},"required":["id","name","fieldKey","description","placeholder","fieldType","required","config","defaultValue","displayOrder","categoryId","createdAt","updatedAt"]},"description":"Custom fields of this contract type"}},"required":["id","name","description","organisationId","isDefault","source","sourceTemplateId","sourceTemplateSlug","entityStatus","createdAt","updatedAt","fields"],"description":"Contract type stored in Contracko"}},"required":["contractType"]}}}},"400":{"description":"Request validation failed (payload, query, or path format is invalid).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"validation_failed":{"summary":"Invalid input payload","value":{"code":"BAD_REQUEST","message":"Request validation failed","data":{"issues":[{"path":["files",0,"mimeType"],"message":"Invalid MIME type."}]}}}}}}},"401":{"description":"Authentication failed (missing, invalid, revoked, or expired API key).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"missing_api_key":{"summary":"No API key header provided","value":{"code":"UNAUTHORIZED","message":"Missing API key. Send x-contracko-api-key or Authorization: Bearer <key>."}}}}}},"403":{"description":"Access denied because the API key does not include the required access for this operation.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"missing_scope":{"summary":"API key does not have access","value":{"code":"FORBIDDEN","message":"This API key does not have access to this endpoint.","data":{"requiredScopes":["required:scope"],"availableScopes":["resource:read"]}}}}}}},"404":{"description":"The requested resource was not found.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"not_found":{"summary":"Resource not found","value":{"code":"NOT_FOUND","message":"Resource not found."}}}}}},"429":{"description":"Retry later because the request rate limit was reached.","headers":{"Retry-After":{"description":"Number of seconds to wait before retrying the request.","schema":{"type":"string"}},"X-RateLimit-Limit":{"description":"Requests allowed in the current rate-limit window.","schema":{"type":"string"}},"X-RateLimit-Remaining":{"description":"Remaining requests in the current rate-limit window.","schema":{"type":"string"}},"X-RateLimit-Reset":{"description":"Unix timestamp when the current rate-limit window resets.","schema":{"type":"string"}}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"rate_limited":{"summary":"API rate limit reached","value":{"code":"TOO_MANY_REQUESTS","message":"Too many requests. Please try again later."}}}}}},"500":{"description":"The server could not complete the request.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"internal_error":{"summary":"Unhandled server error","value":{"code":"INTERNAL_SERVER_ERROR","message":"Unexpected API error"}}}}}}}},"patch":{"operationId":"contractTypes.update","summary":"Update a contract type","description":"Updates a contract type. Include `fields` to reconcile the full custom-field set, or omit `fields` to leave custom fields unchanged.\n\n- `impact` reports whether the edit changed what AI extraction reads. Contracts already using this type keep their saved values and are never re-read by this call.","tags":["Contract Types"],"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Contract type UUID"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"name":{"type":"string","minLength":1,"maxLength":256,"description":"Contract type name"},"description":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"description":"Optional description"},"fields":{"type":"array","items":{"type":"object","properties":{"name":{"type":"string","minLength":1,"maxLength":255},"fieldKey":{"type":"string","pattern":"^[a-z0-9_]+$"},"description":{"type":"string"},"placeholder":{"type":"string"},"fieldType":{"enum":["text","number","date","boolean","currency","percentage","select","multi_select"],"type":"string"},"required":{"type":"boolean","default":false},"config":{"type":"object","propertyNames":{"type":"string"},"additionalProperties":{"anyOf":[{"anyOf":[{"type":"string"},{"type":"number"},{"type":"boolean"},{"type":"null"}]},{"type":"array","items":{"anyOf":[{"anyOf":[{"type":"string"},{"type":"number"},{"type":"boolean"},{"type":"null"}]},{"type":"array","items":{}},{"type":"object","propertyNames":{"type":"string"},"additionalProperties":{}}]}},{"type":"object","propertyNames":{"type":"string"},"additionalProperties":{"anyOf":[{"anyOf":[{"type":"string"},{"type":"number"},{"type":"boolean"},{"type":"null"}]},{"type":"array","items":{}},{"type":"object","propertyNames":{"type":"string"},"additionalProperties":{}}]}}]},"default":{},"description":"Type-specific settings: select and multi_select need options (string array); number may set min, max and decimalPlaces."},"options":{"type":"array","items":{"type":"string"}},"defaultValue":{"anyOf":[{"anyOf":[{"type":"string"},{"type":"number"},{"type":"boolean"},{"type":"null"}]},{"type":"array","items":{"anyOf":[{"anyOf":[{"type":"string"},{"type":"number"},{"type":"boolean"},{"type":"null"}]},{"type":"array","items":{}},{"type":"object","propertyNames":{"type":"string"},"additionalProperties":{}}]}},{"type":"object","propertyNames":{"type":"string"},"additionalProperties":{"anyOf":[{"anyOf":[{"type":"string"},{"type":"number"},{"type":"boolean"},{"type":"null"}]},{"type":"array","items":{}},{"type":"object","propertyNames":{"type":"string"},"additionalProperties":{}}]}}]},"id":{"type":"string"}},"required":["name","fieldKey","fieldType"]},"description":"Optional full custom-field set to reconcile. Omit this field to leave existing custom fields unchanged."}},"required":["name"],"description":"Input payload for updating a contract type."}}}},"responses":{"200":{"description":"Contract type updated.","content":{"application/json":{"schema":{"type":"object","properties":{"contractType":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"name":{"type":"string"},"description":{"anyOf":[{"type":"string"},{"type":"null"}]},"organisationId":{"type":"string"},"isDefault":{"type":"boolean"},"source":{"enum":["manual","template_adoption","starting_template","ai_generated"],"type":"string"},"sourceTemplateId":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}]},"sourceTemplateSlug":{"anyOf":[{"type":"string"},{"type":"null"}]},"entityStatus":{"anyOf":[{"enum":["pending-review","archived"],"type":"string"},{"type":"null"}],"description":"Read-only review state. AI-created types can be pending-review; any update clears it to null."},"createdAt":{"type":"string","format":"date-time","x-native-type":"date"},"updatedAt":{"type":"string","format":"date-time","x-native-type":"date"},"fields":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"name":{"type":"string"},"fieldKey":{"type":"string"},"description":{"anyOf":[{"type":"string"},{"type":"null"}]},"placeholder":{"anyOf":[{"type":"string"},{"type":"null"}]},"fieldType":{"enum":["text","number","date","boolean","currency","percentage","select","multi_select"],"type":"string"},"required":{"type":"boolean"},"config":{"anyOf":[{"anyOf":[{"type":"string"},{"type":"number"},{"type":"boolean"},{"type":"null"}]},{"type":"object","propertyNames":{"type":"string"},"additionalProperties":{}},{"type":"array","items":{"anyOf":[{},{"type":"null"}]}}]},"defaultValue":{"anyOf":[{"anyOf":[{"anyOf":[{"type":"string"},{"type":"number"},{"type":"boolean"},{"type":"null"}]},{"type":"object","propertyNames":{"type":"string"},"additionalProperties":{}},{"type":"array","items":{"anyOf":[{},{"type":"null"}]}}]},{"type":"null"}]},"displayOrder":{"type":"integer","minimum":-2147483648,"maximum":2147483647},"categoryId":{"type":"string","format":"uuid"},"createdAt":{"type":"string","format":"date-time","x-native-type":"date"},"updatedAt":{"type":"string","format":"date-time","x-native-type":"date"}},"required":["id","name","fieldKey","description","placeholder","fieldType","required","config","defaultValue","displayOrder","categoryId","createdAt","updatedAt"]},"description":"Custom fields of this contract type"}},"required":["id","name","description","organisationId","isDefault","source","sourceTemplateId","sourceTemplateSlug","entityStatus","createdAt","updatedAt","fields"],"description":"Contract type stored in Contracko"},"impact":{"type":"object","properties":{"extractionSchemaChanged":{"type":"boolean","description":"Whether this edit changed what AI extraction reads for this contract type"},"changedFieldKeys":{"type":"array","items":{"type":"string"},"description":"Information field keys added, removed, or redefined by this edit"},"existingContractsReprocessed":{"const":false,"description":"Editing a contract type never re-reads documents on existing contracts"},"existingContractValuesChanged":{"const":false,"description":"Editing a contract type never rewrites values already saved on contracts"},"reprocessingRecommended":{"type":"boolean","description":"Whether re-reading affected documents would now produce different suggestions"},"recommendedNextAction":{"enum":["reprocess_relevant_documents","none"],"type":"string","description":"Suggested follow-up for this edit"},"applicationRequiresExplicitApproval":{"const":true,"description":"Findings are only saved by an explicit apply call carrying an approval grant; grants are issued to clients that declare they can ask a person to approve the exact selection"},"previousExtractionSchemaFingerprint":{"type":"string","description":"Fingerprint of the extraction-relevant field definitions before this edit"},"extractionSchemaFingerprint":{"type":"string","description":"Fingerprint of the extraction-relevant field definitions after this edit"}},"required":["extractionSchemaChanged","changedFieldKeys","existingContractsReprocessed","existingContractValuesChanged","reprocessingRecommended","recommendedNextAction","applicationRequiresExplicitApproval","previousExtractionSchemaFingerprint","extractionSchemaFingerprint"],"description":"What this edit did, and did not, do to contracts already using this type"}},"required":["contractType","impact"]}}}},"400":{"description":"Request validation failed (payload, query, or path format is invalid).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"validation_failed":{"summary":"Invalid input payload","value":{"code":"BAD_REQUEST","message":"Request validation failed","data":{"issues":[{"path":["files",0,"mimeType"],"message":"Invalid MIME type."}]}}}}}}},"401":{"description":"Authentication failed (missing, invalid, revoked, or expired API key).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"missing_api_key":{"summary":"No API key header provided","value":{"code":"UNAUTHORIZED","message":"Missing API key. Send x-contracko-api-key or Authorization: Bearer <key>."}}}}}},"403":{"description":"Access denied because the API key does not include the required access for this operation.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"missing_scope":{"summary":"API key does not have access","value":{"code":"FORBIDDEN","message":"This API key does not have access to this endpoint.","data":{"requiredScopes":["required:scope"],"availableScopes":["resource:read"]}}}}}}},"404":{"description":"The requested resource was not found.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"not_found":{"summary":"Resource not found","value":{"code":"NOT_FOUND","message":"Resource not found."}}}}}},"409":{"description":"A previous request with the same idempotency key is still being processed.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"idempotency_conflict":{"summary":"Idempotency key already processing","value":{"code":"CONFLICT","message":"Idempotency-Key is already being processed. Retry shortly."}}}}}},"422":{"description":"Request is well-formed but contains values the API cannot process.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"semantic_validation_failed":{"summary":"Request values are incompatible","value":{"code":"UNPROCESSABLE_CONTENT","message":"Request contains values that cannot be processed."}}}}}},"429":{"description":"Retry later because the request rate limit was reached.","headers":{"Retry-After":{"description":"Number of seconds to wait before retrying the request.","schema":{"type":"string"}},"X-RateLimit-Limit":{"description":"Requests allowed in the current rate-limit window.","schema":{"type":"string"}},"X-RateLimit-Remaining":{"description":"Remaining requests in the current rate-limit window.","schema":{"type":"string"}},"X-RateLimit-Reset":{"description":"Unix timestamp when the current rate-limit window resets.","schema":{"type":"string"}}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"rate_limited":{"summary":"API rate limit reached","value":{"code":"TOO_MANY_REQUESTS","message":"Too many requests. Please try again later."}}}}}},"500":{"description":"The server could not complete the request.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"internal_error":{"summary":"Unhandled server error","value":{"code":"INTERNAL_SERVER_ERROR","message":"Unexpected API error"}}}}}}}},"delete":{"operationId":"contractTypes.delete","summary":"Delete a contract type","description":"Permanently deletes a non-default contract type and its custom-field definitions.\n\n- Contracts assigned to the deleted type are left unassigned. Existing custom-field values remain stored but are no longer associated with active field definitions.\n- Deleting a type after a parser batch is queued can cause that batch to fail because its requested extraction schema no longer exists.","tags":["Contract Types"],"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Contract type UUID"}}],"requestBody":{"required":false,"content":{"application/json":{"schema":{"type":"object","properties":{},"required":[]}}}},"responses":{"200":{"description":"Contract type deleted.","content":{"application/json":{"schema":{"type":"object","properties":{"contractType":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"name":{"type":"string"},"description":{"anyOf":[{"type":"string"},{"type":"null"}]},"organisationId":{"type":"string"},"isDefault":{"type":"boolean"},"source":{"enum":["manual","template_adoption","starting_template","ai_generated"],"type":"string"},"sourceTemplateId":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}]},"sourceTemplateSlug":{"anyOf":[{"type":"string"},{"type":"null"}]},"entityStatus":{"anyOf":[{"enum":["pending-review","archived"],"type":"string"},{"type":"null"}],"description":"Read-only review state. AI-created types can be pending-review; any update clears it to null."},"createdAt":{"type":"string","format":"date-time","x-native-type":"date"},"updatedAt":{"type":"string","format":"date-time","x-native-type":"date"},"fields":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"name":{"type":"string"},"fieldKey":{"type":"string"},"description":{"anyOf":[{"type":"string"},{"type":"null"}]},"placeholder":{"anyOf":[{"type":"string"},{"type":"null"}]},"fieldType":{"enum":["text","number","date","boolean","currency","percentage","select","multi_select"],"type":"string"},"required":{"type":"boolean"},"config":{"anyOf":[{"anyOf":[{"type":"string"},{"type":"number"},{"type":"boolean"},{"type":"null"}]},{"type":"object","propertyNames":{"type":"string"},"additionalProperties":{}},{"type":"array","items":{"anyOf":[{},{"type":"null"}]}}]},"defaultValue":{"anyOf":[{"anyOf":[{"anyOf":[{"type":"string"},{"type":"number"},{"type":"boolean"},{"type":"null"}]},{"type":"object","propertyNames":{"type":"string"},"additionalProperties":{}},{"type":"array","items":{"anyOf":[{},{"type":"null"}]}}]},{"type":"null"}]},"displayOrder":{"type":"integer","minimum":-2147483648,"maximum":2147483647},"categoryId":{"type":"string","format":"uuid"},"createdAt":{"type":"string","format":"date-time","x-native-type":"date"},"updatedAt":{"type":"string","format":"date-time","x-native-type":"date"}},"required":["id","name","fieldKey","description","placeholder","fieldType","required","config","defaultValue","displayOrder","categoryId","createdAt","updatedAt"]},"description":"Custom fields of this contract type"}},"required":["id","name","description","organisationId","isDefault","source","sourceTemplateId","sourceTemplateSlug","entityStatus","createdAt","updatedAt","fields"],"description":"Contract type stored in Contracko"}},"required":["contractType"]}}}},"400":{"description":"Request validation failed (payload, query, or path format is invalid).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"validation_failed":{"summary":"Invalid input payload","value":{"code":"BAD_REQUEST","message":"Request validation failed","data":{"issues":[{"path":["files",0,"mimeType"],"message":"Invalid MIME type."}]}}}}}}},"401":{"description":"Authentication failed (missing, invalid, revoked, or expired API key).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"missing_api_key":{"summary":"No API key header provided","value":{"code":"UNAUTHORIZED","message":"Missing API key. Send x-contracko-api-key or Authorization: Bearer <key>."}}}}}},"403":{"description":"Access denied because the API key does not include the required access for this operation.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"missing_scope":{"summary":"API key does not have access","value":{"code":"FORBIDDEN","message":"This API key does not have access to this endpoint.","data":{"requiredScopes":["required:scope"],"availableScopes":["resource:read"]}}}}}}},"404":{"description":"The requested resource was not found.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"not_found":{"summary":"Resource not found","value":{"code":"NOT_FOUND","message":"Resource not found."}}}}}},"409":{"description":"A previous request with the same idempotency key is still being processed.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"idempotency_conflict":{"summary":"Idempotency key already processing","value":{"code":"CONFLICT","message":"Idempotency-Key is already being processed. Retry shortly."}}}}}},"429":{"description":"Retry later because the request rate limit was reached.","headers":{"Retry-After":{"description":"Number of seconds to wait before retrying the request.","schema":{"type":"string"}},"X-RateLimit-Limit":{"description":"Requests allowed in the current rate-limit window.","schema":{"type":"string"}},"X-RateLimit-Remaining":{"description":"Remaining requests in the current rate-limit window.","schema":{"type":"string"}},"X-RateLimit-Reset":{"description":"Unix timestamp when the current rate-limit window resets.","schema":{"type":"string"}}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"rate_limited":{"summary":"API rate limit reached","value":{"code":"TOO_MANY_REQUESTS","message":"Too many requests. Please try again later."}}}}}},"500":{"description":"The server could not complete the request.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"internal_error":{"summary":"Unhandled server error","value":{"code":"INTERNAL_SERVER_ERROR","message":"Unexpected API error"}}}}}}}}},"/parser/preflight":{"post":{"operationId":"parser.preflight","summary":"Check parser availability and estimated usage","description":"Validate one or more files before upload and return the estimated usage for the batch.","tags":["Parsing API"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"runKind":{"enum":["extraction","review"],"type":"string","description":"Request type. extraction performs structured extraction only; review adds AI analysis and costs extra credits."},"outputLanguage":{"enum":["source","en","nl","de","fr","es","it","pt","zh-Hans","zh-Hant","ja","ko","ar","hi","bn","ta","te","mr","ur","id","vi","th","pl","sv","da","no","fi","tr","ru","uk","ro","cs","hu","el"],"type":"string","description":"Optional AI output language. Omit to use the workspace default; use source to preserve the document language."},"outputTemplateId":{"enum":["standard"],"type":"string","description":"Export layout template. standard keeps the default Contracko parser columns."},"deidentification":{"type":"object","properties":{"policyVersionId":{"const":"contract-safe-v1"},"consistencyScope":{"const":"document","default":"document"},"overrides":{"type":"array","maxItems":24,"items":{"type":"object","properties":{"match":{"type":"object","properties":{"entityType":{"enum":["person","organisation","email","phone","address","identifier","secret"],"type":"string"},"fieldPath":{"type":"string","minLength":1}}},"action":{"anyOf":[{"type":"object","properties":{"type":{"const":"keep"}},"required":["type"]},{"type":"object","properties":{"type":{"const":"replace"},"strategy":{"const":"linked","default":"linked"}},"required":["type"]},{"type":"object","properties":{"type":{"const":"generalize"},"precision":{"const":"city-country"}},"required":["type","precision"]},{"type":"object","properties":{"type":{"const":"remove"}},"required":["type"]}]}},"required":["match","action"]},"default":[]}},"description":"Optional document-scoped protection policy. Omit for an unprotected result; pass an empty object for the contract-safe default."},"files":{"type":"array","minItems":1,"items":{"type":"object","properties":{"fileName":{"type":"string","minLength":1,"description":"Original file name including extension"},"mimeType":{"type":"string","minLength":1,"description":"RFC MIME type of the source file"},"fileSize":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991,"exclusiveMinimum":0,"description":"File size in bytes"},"pageCountEstimate":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991,"exclusiveMinimum":0,"description":"Optional page count estimate to improve credit estimation"}},"required":["fileName","mimeType","fileSize"],"description":"Request body for creating an upload URL."},"description":"Files to validate for parser processing"}},"required":["files"],"description":"Request body for estimating usage before you queue a batch."},"examples":{"example":{"summary":"Example request","value":{"runKind":"extraction","outputLanguage":"en","outputTemplateId":"standard","files":[{"fileName":"vendor-services-agreement.pdf","mimeType":"application/pdf","fileSize":245761,"pageCountEstimate":4}]}}}}}},"responses":{"200":{"description":"Availability and estimated usage returned.","content":{"application/json":{"schema":{"type":"object","properties":{"creditsNeeded":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"Estimated credits required for this request"},"totalBytes":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"Total request payload size in bytes"},"errors":{"type":"array","items":{"type":"string"},"description":"Validation messages returned during preflight"},"fileCredits":{"type":"array","items":{"type":"object","properties":{"fileName":{"type":"string","minLength":1,"description":"File name from the request"},"credits":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991,"exclusiveMinimum":0,"description":"Credits required for this file"},"baseCredits":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991,"exclusiveMinimum":0,"description":"Base extraction credits for this file"},"analysisCredits":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"Additional review credits for this file"},"index":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"Original file index in the request payload"}},"required":["fileName","credits","baseCredits","analysisCredits","index"]},"description":"Per-file credit breakdown"},"breakdown":{"type":"object","properties":{"extraction":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"Credits for structured extraction"},"analysis":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"Additional credits for AI review analysis"},"outputLanguage":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"Additional credits for output-language conversion, currently included at no surcharge"},"extractionTemplate":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"Additional credits for extraction-template fields, currently included at no surcharge"}},"required":["extraction","analysis","outputLanguage","extractionTemplate"],"description":"Credit breakdown by requested parser capability"},"limits":{"type":"object","properties":{"maxFileBytes":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991,"exclusiveMinimum":0,"description":"Maximum file size accepted per file"},"maxBatchBytes":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991,"exclusiveMinimum":0,"description":"Maximum aggregate batch size"},"maxBatchFiles":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991,"exclusiveMinimum":0,"description":"Maximum number of files per batch"}},"required":["maxFileBytes","maxBatchBytes","maxBatchFiles"]},"balance":{"type":"object","properties":{"allocated":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"Allocated credits in the current billing cycle"},"used":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"Credits consumed in the current billing cycle"},"remaining":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"Credits available for new parser jobs"},"sourcePlanKey":{"type":"string","minLength":1,"description":"Plan identifier associated with this usage window"}},"required":["allocated","used","remaining","sourcePlanKey"]},"concurrency":{"type":"object","properties":{"active":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"Parser batches currently in progress"},"max":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"Maximum concurrent parser batches allowed"}},"required":["active","max"]}},"required":["creditsNeeded","totalBytes","errors","fileCredits","breakdown","limits","balance","concurrency"]},"examples":{"success":{"summary":"Availability and estimated usage returned","value":{"creditsNeeded":1,"totalBytes":245761,"errors":[],"fileCredits":[{"fileName":"vendor-services-agreement.pdf","credits":1,"baseCredits":1,"analysisCredits":0,"index":0}],"breakdown":{"extraction":1,"analysis":0,"outputLanguage":0,"extractionTemplate":0},"limits":{"maxFileBytes":52428800,"maxBatchBytes":262144000,"maxBatchFiles":100},"balance":{"allocated":20,"used":3,"remaining":17,"sourcePlanKey":"trial"},"concurrency":{"active":0,"max":5}}}}}}},"400":{"description":"Request validation failed (payload, query, or path format is invalid).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"validation_failed":{"summary":"Invalid input payload","value":{"code":"BAD_REQUEST","message":"Request validation failed","data":{"issues":[{"path":["files",0,"mimeType"],"message":"Invalid MIME type."}]}}}}}}},"401":{"description":"Authentication failed (missing, invalid, revoked, or expired API key).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"missing_api_key":{"summary":"No API key header provided","value":{"code":"UNAUTHORIZED","message":"Missing API key. Send x-contracko-api-key or Authorization: Bearer <key>."}}}}}},"403":{"description":"Access denied because this API key does not include parsing access or the Parsing API is not available for this workspace.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"missing_parsing_access":{"summary":"API key does not include parsing access","value":{"code":"FORBIDDEN","message":"This API key does not have access to this endpoint.","data":{"requiredScopes":["parser:compute"],"availableScopes":["contract:read"]}}},"parsing_unavailable":{"summary":"Parsing API not available","value":{"code":"FORBIDDEN","message":"Parsing API is not available for this workspace."}},"insufficient_credits":{"summary":"Not enough credits available","value":{"code":"FORBIDDEN","message":"Not enough credits available for this request.","data":{"cause":"PARSER_CREDITS_EXHAUSTED","creditsNeeded":2,"creditsRemaining":1}}}}}}},"429":{"description":"Retry later because the request rate limit was reached or too many parser batches are already running for this workspace.","headers":{"Retry-After":{"description":"Number of seconds to wait before retrying the request.","schema":{"type":"string"}},"X-RateLimit-Limit":{"description":"Requests allowed in the current rate-limit window.","schema":{"type":"string"}},"X-RateLimit-Remaining":{"description":"Remaining requests in the current rate-limit window.","schema":{"type":"string"}},"X-RateLimit-Reset":{"description":"Unix timestamp when the current rate-limit window resets.","schema":{"type":"string"}}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"rate_limited":{"summary":"API rate limit reached","value":{"code":"TOO_MANY_REQUESTS","message":"Too many requests. Please try again later."}},"concurrency_limited":{"summary":"Too many parser batches are running","value":{"code":"TOO_MANY_REQUESTS","message":"Too many parser batches are already running for this workspace. Wait for one to finish and try again."}}}}}},"500":{"description":"The server could not complete the request.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"internal_error":{"summary":"Unhandled server error","value":{"code":"INTERNAL_SERVER_ERROR","message":"Unexpected API error"}}}}}}}}},"/parser/upload-url":{"post":{"operationId":"parser.uploadUrl","summary":"Create an upload URL","description":"Create a signed upload URL for a source file. Upload the file with HTTP PUT, then use the returned `fileKey` when you queue a batch.","tags":["Parsing API"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"fileName":{"type":"string","minLength":1,"description":"Original file name including extension"},"mimeType":{"type":"string","minLength":1,"description":"RFC MIME type of the source file"},"fileSize":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991,"exclusiveMinimum":0,"description":"File size in bytes"},"pageCountEstimate":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991,"exclusiveMinimum":0,"description":"Optional page count estimate to improve credit estimation"}},"required":["fileName","mimeType","fileSize"],"description":"Request body for creating an upload URL."},"examples":{"example":{"summary":"Example request","value":{"fileName":"vendor-services-agreement.pdf","mimeType":"application/pdf","fileSize":245761,"pageCountEstimate":4}}}}}},"responses":{"200":{"description":"Upload URL returned.","content":{"application/json":{"schema":{"type":"object","properties":{"fileKey":{"type":"string","minLength":1,"description":"File reference to include in POST /parser/jobs"},"uploadUrl":{"type":"string","minLength":1,"description":"Single-use signed URL for file upload"},"expiresIn":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991,"exclusiveMinimum":0,"description":"Number of seconds until URL expiration"},"credits":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991,"exclusiveMinimum":0,"description":"Estimated credits for this file"}},"required":["fileKey","uploadUrl","expiresIn","credits"]},"examples":{"success":{"summary":"Upload URL returned","value":{"fileKey":"parser/uploads/org_123/019ce45f-vendor-services-agreement.pdf","uploadUrl":"https://r2.example.com/parser/uploads/org_123/019ce45f-vendor-services-agreement.pdf?X-Amz-Signature=example","expiresIn":3600,"credits":1}}}}}},"400":{"description":"Request validation failed (payload, query, or path format is invalid).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"validation_failed":{"summary":"Invalid input payload","value":{"code":"BAD_REQUEST","message":"Request validation failed","data":{"issues":[{"path":["files",0,"mimeType"],"message":"Invalid MIME type."}]}}}}}}},"401":{"description":"Authentication failed (missing, invalid, revoked, or expired API key).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"missing_api_key":{"summary":"No API key header provided","value":{"code":"UNAUTHORIZED","message":"Missing API key. Send x-contracko-api-key or Authorization: Bearer <key>."}}}}}},"403":{"description":"Access denied because this API key does not include parsing access or the Parsing API is not available for this workspace.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"missing_parsing_access":{"summary":"API key does not include parsing access","value":{"code":"FORBIDDEN","message":"This API key does not have access to this endpoint.","data":{"requiredScopes":["parser:compute"],"availableScopes":["contract:read"]}}},"parsing_unavailable":{"summary":"Parsing API not available","value":{"code":"FORBIDDEN","message":"Parsing API is not available for this workspace."}},"insufficient_credits":{"summary":"Not enough credits available","value":{"code":"FORBIDDEN","message":"Not enough credits available for this request.","data":{"cause":"PARSER_CREDITS_EXHAUSTED","creditsNeeded":2,"creditsRemaining":1}}}}}}},"413":{"description":"Payload is too large for endpoint file-size or batch-size limits.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"payload_too_large":{"summary":"File exceeds allowed size","value":{"code":"PAYLOAD_TOO_LARGE","message":"Uploaded file exceeds the maximum size for this endpoint."}}}}}},"415":{"description":"File type is not supported for the selected operation.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"unsupported_media_type":{"summary":"Unsupported MIME type","value":{"code":"UNSUPPORTED_MEDIA_TYPE","message":"Unsupported file type."}}}}}},"422":{"description":"Request is well-formed but contains values the API cannot process.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"semantic_validation_failed":{"summary":"Request values are incompatible","value":{"code":"UNPROCESSABLE_CONTENT","message":"Request contains values that cannot be processed."}}}}}},"429":{"description":"Retry later because the request rate limit was reached or too many parser batches are already running for this workspace.","headers":{"Retry-After":{"description":"Number of seconds to wait before retrying the request.","schema":{"type":"string"}},"X-RateLimit-Limit":{"description":"Requests allowed in the current rate-limit window.","schema":{"type":"string"}},"X-RateLimit-Remaining":{"description":"Remaining requests in the current rate-limit window.","schema":{"type":"string"}},"X-RateLimit-Reset":{"description":"Unix timestamp when the current rate-limit window resets.","schema":{"type":"string"}}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"rate_limited":{"summary":"API rate limit reached","value":{"code":"TOO_MANY_REQUESTS","message":"Too many requests. Please try again later."}},"concurrency_limited":{"summary":"Too many parser batches are running","value":{"code":"TOO_MANY_REQUESTS","message":"Too many parser batches are already running for this workspace. Wait for one to finish and try again."}}}}}},"500":{"description":"The server could not complete the request.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"internal_error":{"summary":"Unhandled server error","value":{"code":"INTERNAL_SERVER_ERROR","message":"Unexpected API error"}}}}}}}}},"/parser/jobs":{"post":{"operationId":"parser.enqueue","summary":"Queue a parsing job","description":"Queue a parser batch from files you already uploaded with `POST /parser/upload-url`. Returns a batch ID you can poll with `GET /parser/jobs/{batchId}`.","tags":["Parsing API"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"aiInferenceMode":{"enum":["fast","standard"],"type":"string","description":"AI inference mode. Defaults to fast; choose standard for background work."},"outputFormat":{"enum":["json","csv","xlsx"],"type":"string","default":"json","description":"Requested export format for parser output. csv returns a ZIP bundle with one CSV per logical table; xlsx returns a multi-sheet workbook."},"runKind":{"enum":["extraction","review"],"type":"string","description":"Request type. extraction performs structured extraction only; review adds AI analysis and costs extra credits."},"outputLanguage":{"enum":["source","en","nl","de","fr","es","it","pt","zh-Hans","zh-Hant","ja","ko","ar","hi","bn","ta","te","mr","ur","id","vi","th","pl","sv","da","no","fi","tr","ru","uk","ro","cs","hu","el"],"type":"string","description":"Optional AI output language. Omit to use the workspace default; use source to preserve the document language."},"outputTemplateId":{"enum":["standard"],"type":"string","description":"Export layout template. standard keeps the default Contracko parser columns."},"categoryId":{"type":"string","format":"uuid","description":"Optional extraction template / contract type UUID. When provided, custom fields from that template are extracted."},"deidentification":{"type":"object","properties":{"policyVersionId":{"const":"contract-safe-v1"},"consistencyScope":{"const":"document","default":"document"},"overrides":{"type":"array","maxItems":24,"items":{"type":"object","properties":{"match":{"type":"object","properties":{"entityType":{"enum":["person","organisation","email","phone","address","identifier","secret"],"type":"string"},"fieldPath":{"type":"string","minLength":1}}},"action":{"anyOf":[{"type":"object","properties":{"type":{"const":"keep"}},"required":["type"]},{"type":"object","properties":{"type":{"const":"replace"},"strategy":{"const":"linked","default":"linked"}},"required":["type"]},{"type":"object","properties":{"type":{"const":"generalize"},"precision":{"const":"city-country"}},"required":["type","precision"]},{"type":"object","properties":{"type":{"const":"remove"}},"required":["type"]}]}},"required":["match","action"]},"default":[]}},"description":"Optional document-scoped protection policy. The resolved version is applied before previews and exports are produced."},"files":{"type":"array","minItems":1,"items":{"type":"object","properties":{"fileName":{"type":"string","minLength":1,"description":"Original file name including extension"},"mimeType":{"type":"string","minLength":1,"description":"RFC MIME type of the source file"},"fileSize":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991,"exclusiveMinimum":0,"description":"File size in bytes"},"pageCountEstimate":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991,"exclusiveMinimum":0,"description":"Optional page count estimate to improve credit estimation"},"fileKey":{"type":"string","minLength":1,"description":"Parser upload key returned by POST /parser/upload-url"}},"required":["fileName","mimeType","fileSize","fileKey"]},"description":"Files to include in the parser batch"}},"required":["files"],"description":"Request body for queueing a parser batch."},"examples":{"example":{"summary":"Example request","value":{"outputFormat":"json","runKind":"extraction","outputLanguage":"en","outputTemplateId":"standard","files":[{"fileName":"vendor-services-agreement.pdf","mimeType":"application/pdf","fileSize":245761,"fileKey":"parser/uploads/org_123/019ce45f-vendor-services-agreement.pdf","pageCountEstimate":4}]}}}}}},"responses":{"200":{"description":"Batch queued.","content":{"application/json":{"schema":{"type":"object","properties":{"batchId":{"type":"string","minLength":1,"description":"Batch ID to use with GET /parser/jobs/{batchId}"},"creditsNeeded":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"Credits reserved for this batch"}},"required":["batchId","creditsNeeded"]},"examples":{"success":{"summary":"Batch queued","value":{"batchId":"62a5e2e7-1b8f-45e0-abed-17f01ba4eb1e","creditsNeeded":1}}}}}},"400":{"description":"Request validation failed (payload, query, or path format is invalid).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"validation_failed":{"summary":"Invalid input payload","value":{"code":"BAD_REQUEST","message":"Request validation failed","data":{"issues":[{"path":["files",0,"mimeType"],"message":"Invalid MIME type."}]}}}}}}},"401":{"description":"Authentication failed (missing, invalid, revoked, or expired API key).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"missing_api_key":{"summary":"No API key header provided","value":{"code":"UNAUTHORIZED","message":"Missing API key. Send x-contracko-api-key or Authorization: Bearer <key>."}}}}}},"403":{"description":"Access denied because this API key does not include parsing access or the Parsing API is not available for this workspace.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"missing_parsing_access":{"summary":"API key does not include parsing access","value":{"code":"FORBIDDEN","message":"This API key does not have access to this endpoint.","data":{"requiredScopes":["parser:compute"],"availableScopes":["contract:read"]}}},"parsing_unavailable":{"summary":"Parsing API not available","value":{"code":"FORBIDDEN","message":"Parsing API is not available for this workspace."}},"insufficient_credits":{"summary":"Not enough credits available","value":{"code":"FORBIDDEN","message":"Not enough credits available for this request.","data":{"cause":"PARSER_CREDITS_EXHAUSTED","creditsNeeded":2,"creditsRemaining":1}}}}}}},"429":{"description":"Retry later because the request rate limit was reached or too many parser batches are already running for this workspace.","headers":{"Retry-After":{"description":"Number of seconds to wait before retrying the request.","schema":{"type":"string"}},"X-RateLimit-Limit":{"description":"Requests allowed in the current rate-limit window.","schema":{"type":"string"}},"X-RateLimit-Remaining":{"description":"Remaining requests in the current rate-limit window.","schema":{"type":"string"}},"X-RateLimit-Reset":{"description":"Unix timestamp when the current rate-limit window resets.","schema":{"type":"string"}}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"rate_limited":{"summary":"API rate limit reached","value":{"code":"TOO_MANY_REQUESTS","message":"Too many requests. Please try again later."}},"concurrency_limited":{"summary":"Too many parser batches are running","value":{"code":"TOO_MANY_REQUESTS","message":"Too many parser batches are already running for this workspace. Wait for one to finish and try again."}}}}}},"500":{"description":"The server could not complete the request.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"internal_error":{"summary":"Unhandled server error","value":{"code":"INTERNAL_SERVER_ERROR","message":"Unexpected API error"}}}}}}}},"get":{"operationId":"parser.recent","summary":"List parsing batches","description":"List parser batches in reverse chronological order.\n\n- Query example: `/parser/jobs?limit=10&offset=0`","tags":["Parsing API"],"parameters":[{"name":"limit","in":"query","schema":{"type":"integer","minimum":1,"maximum":50,"default":10,"description":"Page size (max 50)"},"allowEmptyValue":true,"allowReserved":true},{"name":"offset","in":"query","schema":{"type":"integer","minimum":0,"maximum":9007199254740991,"default":0,"description":"Pagination offset"},"allowEmptyValue":true,"allowReserved":true}],"responses":{"200":{"description":"Parser batches returned.","content":{"application/json":{"schema":{"type":"object","properties":{"items":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string","format":"uuid","description":"Batch UUID"},"status":{"type":"string","minLength":1,"description":"Batch status"},"outputFormat":{"type":"string","minLength":1,"description":"Requested output format"},"creditCost":{"anyOf":[{"type":"integer","minimum":0,"maximum":9007199254740991},{"type":"null"}],"description":"Parser credits billed to this Contracko Parser batch, when available"},"totalFiles":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"Total files in the batch"},"completedFiles":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"Files completed so far"},"retentionExpiresAt":{"type":"string","format":"date-time","description":"ISO-8601 artifact retention expiration timestamp"},"createdAt":{"type":"string","format":"date-time","description":"ISO-8601 creation timestamp"},"metadata":{"description":"Additional batch metadata"}},"required":["id","status","outputFormat","creditCost","totalFiles","completedFiles","retentionExpiresAt","createdAt"]},"description":"Parser batches in the requested page"},"limit":{"type":"integer","minimum":1,"maximum":9007199254740991,"description":"Page size used in this response"},"offset":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"Offset used in this response"},"hasMore":{"type":"boolean","description":"Whether additional pages are available"},"total":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"Total parser batches available for the organisation"},"page":{"type":"integer","minimum":1,"maximum":9007199254740991,"description":"Current 1-based page index"},"pageCount":{"type":"integer","minimum":1,"maximum":9007199254740991,"description":"Total number of pages"},"start":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"1-based inclusive index of first row in this page"},"end":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"1-based inclusive index of last row in this page"}},"required":["items","limit","offset","hasMore","total","page","pageCount","start","end"]},"examples":{"success":{"summary":"Parser batches returned","value":{"items":[{"id":"62a5e2e7-1b8f-45e0-abed-17f01ba4eb1e","status":"completed","outputFormat":"json","creditCost":1,"totalFiles":1,"completedFiles":1,"retentionExpiresAt":"2026-03-20T10:30:00.000Z","createdAt":"2026-03-13T10:30:00.000Z","metadata":{"customFieldsIncluded":false}}],"limit":10,"offset":0,"hasMore":false,"total":1,"page":1,"pageCount":1,"start":1,"end":1}}}}}},"400":{"description":"Request validation failed (payload, query, or path format is invalid).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"validation_failed":{"summary":"Invalid input payload","value":{"code":"BAD_REQUEST","message":"Request validation failed","data":{"issues":[{"path":["files",0,"mimeType"],"message":"Invalid MIME type."}]}}}}}}},"401":{"description":"Authentication failed (missing, invalid, revoked, or expired API key).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"missing_api_key":{"summary":"No API key header provided","value":{"code":"UNAUTHORIZED","message":"Missing API key. Send x-contracko-api-key or Authorization: Bearer <key>."}}}}}},"403":{"description":"Access denied because this API key does not include parsing access or the Parsing API is not available for this workspace.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"missing_parsing_access":{"summary":"API key does not include parsing access","value":{"code":"FORBIDDEN","message":"This API key does not have access to this endpoint.","data":{"requiredScopes":["parser:compute"],"availableScopes":["contract:read"]}}},"parsing_unavailable":{"summary":"Parsing API not available","value":{"code":"FORBIDDEN","message":"Parsing API is not available for this workspace."}},"insufficient_credits":{"summary":"Not enough credits available","value":{"code":"FORBIDDEN","message":"Not enough credits available for this request.","data":{"cause":"PARSER_CREDITS_EXHAUSTED","creditsNeeded":2,"creditsRemaining":1}}}}}}},"429":{"description":"Retry later because the request rate limit was reached or too many parser batches are already running for this workspace.","headers":{"Retry-After":{"description":"Number of seconds to wait before retrying the request.","schema":{"type":"string"}},"X-RateLimit-Limit":{"description":"Requests allowed in the current rate-limit window.","schema":{"type":"string"}},"X-RateLimit-Remaining":{"description":"Remaining requests in the current rate-limit window.","schema":{"type":"string"}},"X-RateLimit-Reset":{"description":"Unix timestamp when the current rate-limit window resets.","schema":{"type":"string"}}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"rate_limited":{"summary":"API rate limit reached","value":{"code":"TOO_MANY_REQUESTS","message":"Too many requests. Please try again later."}},"concurrency_limited":{"summary":"Too many parser batches are running","value":{"code":"TOO_MANY_REQUESTS","message":"Too many parser batches are already running for this workspace. Wait for one to finish and try again."}}}}}},"500":{"description":"The server could not complete the request.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"internal_error":{"summary":"Unhandled server error","value":{"code":"INTERNAL_SERVER_ERROR","message":"Unexpected API error"}}}}}}}}},"/parser/extractions":{"post":{"operationId":"parser.extractions","summary":"Queue an AI extraction","description":"Queue an AI extraction batch from files you already uploaded with `POST /parser/upload-url`. Supports output language, extraction template, output format, and output template options.","tags":["Parsing API"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"aiInferenceMode":{"enum":["fast","standard"],"type":"string","description":"AI inference mode. Defaults to fast; choose standard for background work."},"outputFormat":{"enum":["json","csv","xlsx"],"type":"string","default":"json","description":"Requested export format for parser output. csv returns a ZIP bundle with one CSV per logical table; xlsx returns a multi-sheet workbook."},"runKind":{"enum":["extraction","review"],"type":"string","description":"Request type. extraction performs structured extraction only; review adds AI analysis and costs extra credits."},"outputLanguage":{"enum":["source","en","nl","de","fr","es","it","pt","zh-Hans","zh-Hant","ja","ko","ar","hi","bn","ta","te","mr","ur","id","vi","th","pl","sv","da","no","fi","tr","ru","uk","ro","cs","hu","el"],"type":"string","description":"Optional AI output language. Omit to use the workspace default; use source to preserve the document language."},"outputTemplateId":{"enum":["standard"],"type":"string","description":"Export layout template. standard keeps the default Contracko parser columns."},"categoryId":{"type":"string","format":"uuid","description":"Optional extraction template / contract type UUID. When provided, custom fields from that template are extracted."},"deidentification":{"type":"object","properties":{"policyVersionId":{"const":"contract-safe-v1"},"consistencyScope":{"const":"document","default":"document"},"overrides":{"type":"array","maxItems":24,"items":{"type":"object","properties":{"match":{"type":"object","properties":{"entityType":{"enum":["person","organisation","email","phone","address","identifier","secret"],"type":"string"},"fieldPath":{"type":"string","minLength":1}}},"action":{"anyOf":[{"type":"object","properties":{"type":{"const":"keep"}},"required":["type"]},{"type":"object","properties":{"type":{"const":"replace"},"strategy":{"const":"linked","default":"linked"}},"required":["type"]},{"type":"object","properties":{"type":{"const":"generalize"},"precision":{"const":"city-country"}},"required":["type","precision"]},{"type":"object","properties":{"type":{"const":"remove"}},"required":["type"]}]}},"required":["match","action"]},"default":[]}},"description":"Optional document-scoped protection policy. The resolved version is applied before previews and exports are produced."},"files":{"type":"array","minItems":1,"items":{"type":"object","properties":{"fileName":{"type":"string","minLength":1,"description":"Original file name including extension"},"mimeType":{"type":"string","minLength":1,"description":"RFC MIME type of the source file"},"fileSize":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991,"exclusiveMinimum":0,"description":"File size in bytes"},"pageCountEstimate":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991,"exclusiveMinimum":0,"description":"Optional page count estimate to improve credit estimation"},"fileKey":{"type":"string","minLength":1,"description":"Parser upload key returned by POST /parser/upload-url"}},"required":["fileName","mimeType","fileSize","fileKey"]},"description":"Files to include in the parser batch"}},"required":["files"],"description":"Request body for queueing a parser batch."},"examples":{"example":{"summary":"Example request","value":{"outputFormat":"json","runKind":"extraction","outputLanguage":"en","outputTemplateId":"standard","files":[{"fileName":"vendor-services-agreement.pdf","mimeType":"application/pdf","fileSize":245761,"fileKey":"parser/uploads/org_123/019ce45f-vendor-services-agreement.pdf","pageCountEstimate":4}]}}}}}},"responses":{"200":{"description":"Extraction batch queued.","content":{"application/json":{"schema":{"type":"object","properties":{"batchId":{"type":"string","minLength":1,"description":"Batch ID to use with GET /parser/jobs/{batchId}"},"creditsNeeded":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"Credits reserved for this batch"}},"required":["batchId","creditsNeeded"]},"examples":{"success":{"summary":"Extraction batch queued","value":{"batchId":"62a5e2e7-1b8f-45e0-abed-17f01ba4eb1e","creditsNeeded":1}}}}}},"400":{"description":"Request validation failed (payload, query, or path format is invalid).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"validation_failed":{"summary":"Invalid input payload","value":{"code":"BAD_REQUEST","message":"Request validation failed","data":{"issues":[{"path":["files",0,"mimeType"],"message":"Invalid MIME type."}]}}}}}}},"401":{"description":"Authentication failed (missing, invalid, revoked, or expired API key).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"missing_api_key":{"summary":"No API key header provided","value":{"code":"UNAUTHORIZED","message":"Missing API key. Send x-contracko-api-key or Authorization: Bearer <key>."}}}}}},"403":{"description":"Access denied because this API key does not include parsing access or the Parsing API is not available for this workspace.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"missing_parsing_access":{"summary":"API key does not include parsing access","value":{"code":"FORBIDDEN","message":"This API key does not have access to this endpoint.","data":{"requiredScopes":["parser:compute"],"availableScopes":["contract:read"]}}},"parsing_unavailable":{"summary":"Parsing API not available","value":{"code":"FORBIDDEN","message":"Parsing API is not available for this workspace."}},"insufficient_credits":{"summary":"Not enough credits available","value":{"code":"FORBIDDEN","message":"Not enough credits available for this request.","data":{"cause":"PARSER_CREDITS_EXHAUSTED","creditsNeeded":2,"creditsRemaining":1}}}}}}},"429":{"description":"Retry later because the request rate limit was reached or too many parser batches are already running for this workspace.","headers":{"Retry-After":{"description":"Number of seconds to wait before retrying the request.","schema":{"type":"string"}},"X-RateLimit-Limit":{"description":"Requests allowed in the current rate-limit window.","schema":{"type":"string"}},"X-RateLimit-Remaining":{"description":"Remaining requests in the current rate-limit window.","schema":{"type":"string"}},"X-RateLimit-Reset":{"description":"Unix timestamp when the current rate-limit window resets.","schema":{"type":"string"}}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"rate_limited":{"summary":"API rate limit reached","value":{"code":"TOO_MANY_REQUESTS","message":"Too many requests. Please try again later."}},"concurrency_limited":{"summary":"Too many parser batches are running","value":{"code":"TOO_MANY_REQUESTS","message":"Too many parser batches are already running for this workspace. Wait for one to finish and try again."}}}}}},"500":{"description":"The server could not complete the request.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"internal_error":{"summary":"Unhandled server error","value":{"code":"INTERNAL_SERVER_ERROR","message":"Unexpected API error"}}}}}}}}},"/parser/reviews":{"post":{"operationId":"parser.reviews","summary":"Queue an AI contract review","description":"Queue an AI contract review batch. This dedicated endpoint is the product-facing alias for extraction plus AI analysis/review output and uses the same polling flow as parser jobs.","tags":["Parsing API"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"aiInferenceMode":{"enum":["fast","standard"],"type":"string","description":"AI inference mode. Defaults to fast; choose standard for background work."},"outputFormat":{"enum":["json","csv","xlsx"],"type":"string","default":"json","description":"Requested export format for parser output. csv returns a ZIP bundle with one CSV per logical table; xlsx returns a multi-sheet workbook."},"runKind":{"enum":["extraction","review"],"type":"string","description":"Request type. extraction performs structured extraction only; review adds AI analysis and costs extra credits."},"outputLanguage":{"enum":["source","en","nl","de","fr","es","it","pt","zh-Hans","zh-Hant","ja","ko","ar","hi","bn","ta","te","mr","ur","id","vi","th","pl","sv","da","no","fi","tr","ru","uk","ro","cs","hu","el"],"type":"string","description":"Optional AI output language. Omit to use the workspace default; use source to preserve the document language."},"outputTemplateId":{"enum":["standard"],"type":"string","description":"Export layout template. standard keeps the default Contracko parser columns."},"categoryId":{"type":"string","format":"uuid","description":"Optional extraction template / contract type UUID. When provided, custom fields from that template are extracted."},"deidentification":{"type":"object","properties":{"policyVersionId":{"const":"contract-safe-v1"},"consistencyScope":{"const":"document","default":"document"},"overrides":{"type":"array","maxItems":24,"items":{"type":"object","properties":{"match":{"type":"object","properties":{"entityType":{"enum":["person","organisation","email","phone","address","identifier","secret"],"type":"string"},"fieldPath":{"type":"string","minLength":1}}},"action":{"anyOf":[{"type":"object","properties":{"type":{"const":"keep"}},"required":["type"]},{"type":"object","properties":{"type":{"const":"replace"},"strategy":{"const":"linked","default":"linked"}},"required":["type"]},{"type":"object","properties":{"type":{"const":"generalize"},"precision":{"const":"city-country"}},"required":["type","precision"]},{"type":"object","properties":{"type":{"const":"remove"}},"required":["type"]}]}},"required":["match","action"]},"default":[]}},"description":"Optional document-scoped protection policy. The resolved version is applied before previews and exports are produced."},"files":{"type":"array","minItems":1,"items":{"type":"object","properties":{"fileName":{"type":"string","minLength":1,"description":"Original file name including extension"},"mimeType":{"type":"string","minLength":1,"description":"RFC MIME type of the source file"},"fileSize":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991,"exclusiveMinimum":0,"description":"File size in bytes"},"pageCountEstimate":{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991,"exclusiveMinimum":0,"description":"Optional page count estimate to improve credit estimation"},"fileKey":{"type":"string","minLength":1,"description":"Parser upload key returned by POST /parser/upload-url"}},"required":["fileName","mimeType","fileSize","fileKey"]},"description":"Files to include in the parser batch"}},"required":["files"],"description":"Request body for queueing a parser batch."},"examples":{"example":{"summary":"Example request","value":{"outputFormat":"json","runKind":"review","outputLanguage":"en","outputTemplateId":"standard","files":[{"fileName":"vendor-services-agreement.pdf","mimeType":"application/pdf","fileSize":245761,"fileKey":"parser/uploads/org_123/019ce45f-vendor-services-agreement.pdf","pageCountEstimate":4}]}}}}}},"responses":{"200":{"description":"Review batch queued.","content":{"application/json":{"schema":{"type":"object","properties":{"batchId":{"type":"string","minLength":1,"description":"Batch ID to use with GET /parser/jobs/{batchId}"},"creditsNeeded":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"Credits reserved for this batch"}},"required":["batchId","creditsNeeded"]},"examples":{"success":{"summary":"Review batch queued","value":{"batchId":"62a5e2e7-1b8f-45e0-abed-17f01ba4eb1e","creditsNeeded":1}}}}}},"400":{"description":"Request validation failed (payload, query, or path format is invalid).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"validation_failed":{"summary":"Invalid input payload","value":{"code":"BAD_REQUEST","message":"Request validation failed","data":{"issues":[{"path":["files",0,"mimeType"],"message":"Invalid MIME type."}]}}}}}}},"401":{"description":"Authentication failed (missing, invalid, revoked, or expired API key).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"missing_api_key":{"summary":"No API key header provided","value":{"code":"UNAUTHORIZED","message":"Missing API key. Send x-contracko-api-key or Authorization: Bearer <key>."}}}}}},"403":{"description":"Access denied because this API key does not include parsing access or the Parsing API is not available for this workspace.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"missing_parsing_access":{"summary":"API key does not include parsing access","value":{"code":"FORBIDDEN","message":"This API key does not have access to this endpoint.","data":{"requiredScopes":["parser:compute"],"availableScopes":["contract:read"]}}},"parsing_unavailable":{"summary":"Parsing API not available","value":{"code":"FORBIDDEN","message":"Parsing API is not available for this workspace."}},"insufficient_credits":{"summary":"Not enough credits available","value":{"code":"FORBIDDEN","message":"Not enough credits available for this request.","data":{"cause":"PARSER_CREDITS_EXHAUSTED","creditsNeeded":2,"creditsRemaining":1}}}}}}},"429":{"description":"Retry later because the request rate limit was reached or too many parser batches are already running for this workspace.","headers":{"Retry-After":{"description":"Number of seconds to wait before retrying the request.","schema":{"type":"string"}},"X-RateLimit-Limit":{"description":"Requests allowed in the current rate-limit window.","schema":{"type":"string"}},"X-RateLimit-Remaining":{"description":"Remaining requests in the current rate-limit window.","schema":{"type":"string"}},"X-RateLimit-Reset":{"description":"Unix timestamp when the current rate-limit window resets.","schema":{"type":"string"}}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"rate_limited":{"summary":"API rate limit reached","value":{"code":"TOO_MANY_REQUESTS","message":"Too many requests. Please try again later."}},"concurrency_limited":{"summary":"Too many parser batches are running","value":{"code":"TOO_MANY_REQUESTS","message":"Too many parser batches are already running for this workspace. Wait for one to finish and try again."}}}}}},"500":{"description":"The server could not complete the request.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"internal_error":{"summary":"Unhandled server error","value":{"code":"INTERNAL_SERVER_ERROR","message":"Unexpected API error"}}}}}}}}},"/parser/credits":{"get":{"operationId":"parser.credits","summary":"Retrieve current usage","description":"Return current usage, remaining credits, and parser batch concurrency for the workspace.","tags":["Parsing API"],"responses":{"200":{"description":"Current usage returned.","content":{"application/json":{"schema":{"type":"object","properties":{"allocated":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"Allocated credits in the current billing cycle"},"used":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"Consumed credits in the current billing cycle"},"remaining":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"Available credits for new parser work"},"sourcePlanKey":{"type":"string","minLength":1,"description":"Plan identifier associated with this usage window"},"refreshesAt":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"description":"ISO-8601 refresh timestamp for credits"},"planName":{"type":"string","minLength":1,"description":"Human-readable name of the current parsing plan"},"maxConcurrency":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"Maximum concurrent parser batches"},"activeBatches":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"Current number of active parser batches"},"isInTrial":{"type":"boolean","description":"Whether the parser subscription is currently in trial"}},"required":["allocated","used","remaining","sourcePlanKey","refreshesAt","planName","maxConcurrency","activeBatches","isInTrial"]},"examples":{"success":{"summary":"Current usage returned","value":{"allocated":20,"used":4,"remaining":16,"sourcePlanKey":"trial","refreshesAt":null,"planName":"Trial","maxConcurrency":5,"activeBatches":1,"isInTrial":true}}}}}},"401":{"description":"Authentication failed (missing, invalid, revoked, or expired API key).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"missing_api_key":{"summary":"No API key header provided","value":{"code":"UNAUTHORIZED","message":"Missing API key. Send x-contracko-api-key or Authorization: Bearer <key>."}}}}}},"403":{"description":"Access denied because this API key does not include parsing access or the Parsing API is not available for this workspace.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"missing_parsing_access":{"summary":"API key does not include parsing access","value":{"code":"FORBIDDEN","message":"This API key does not have access to this endpoint.","data":{"requiredScopes":["parser:compute"],"availableScopes":["contract:read"]}}},"parsing_unavailable":{"summary":"Parsing API not available","value":{"code":"FORBIDDEN","message":"Parsing API is not available for this workspace."}},"insufficient_credits":{"summary":"Not enough credits available","value":{"code":"FORBIDDEN","message":"Not enough credits available for this request.","data":{"cause":"PARSER_CREDITS_EXHAUSTED","creditsNeeded":2,"creditsRemaining":1}}}}}}},"429":{"description":"Retry later because the request rate limit was reached or too many parser batches are already running for this workspace.","headers":{"Retry-After":{"description":"Number of seconds to wait before retrying the request.","schema":{"type":"string"}},"X-RateLimit-Limit":{"description":"Requests allowed in the current rate-limit window.","schema":{"type":"string"}},"X-RateLimit-Remaining":{"description":"Remaining requests in the current rate-limit window.","schema":{"type":"string"}},"X-RateLimit-Reset":{"description":"Unix timestamp when the current rate-limit window resets.","schema":{"type":"string"}}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"rate_limited":{"summary":"API rate limit reached","value":{"code":"TOO_MANY_REQUESTS","message":"Too many requests. Please try again later."}},"concurrency_limited":{"summary":"Too many parser batches are running","value":{"code":"TOO_MANY_REQUESTS","message":"Too many parser batches are already running for this workspace. Wait for one to finish and try again."}}}}}},"500":{"description":"The server could not complete the request.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"internal_error":{"summary":"Unhandled server error","value":{"code":"INTERNAL_SERVER_ERROR","message":"Unexpected API error"}}}}}}}}},"/parser/jobs/{batchId}":{"get":{"operationId":"parser.detail","summary":"Retrieve batch results","description":"Retrieve the current status, per-file extracted output preview, and download URL for a batch.","tags":["Parsing API"],"parameters":[{"name":"batchId","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Parser batch UUID"}}],"responses":{"200":{"description":"Batch details returned.","content":{"application/json":{"schema":{"type":"object","properties":{"batch":{"type":"object","properties":{"id":{"type":"string","format":"uuid","description":"Batch UUID"},"status":{"type":"string","minLength":1,"description":"Batch processing status"},"outputFormat":{"type":"string","minLength":1,"description":"Batch output format"},"totalFiles":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"Total files in the batch"},"completedFiles":{"type":"integer","minimum":0,"maximum":9007199254740991,"description":"Completed files in the batch"},"creditCost":{"anyOf":[{"type":"integer","minimum":0,"maximum":9007199254740991},{"type":"null"}],"description":"Total Parser credits charged for this Contracko Parser batch"},"retentionExpiresAt":{"type":"string","format":"date-time","description":"ISO-8601 timestamp when artifacts expire"},"createdAt":{"type":"string","format":"date-time","description":"ISO-8601 creation timestamp"},"metadata":{"description":"Additional batch metadata"},"downloadUrl":{"anyOf":[{"type":"string","minLength":1},{"type":"null"}],"description":"Signed URL to download the extracted output when the batch is completed"}},"required":["id","status","outputFormat","totalFiles","completedFiles","creditCost","retentionExpiresAt","createdAt","downloadUrl"]},"items":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string","format":"uuid","description":"Parser item UUID"},"fileName":{"type":"string","minLength":1,"description":"Original file name"},"mimeType":{"type":"string","minLength":1,"description":"MIME type"},"fileSize":{"anyOf":[{"type":"integer","minimum":-9007199254740991,"maximum":9007199254740991,"exclusiveMinimum":0},{"type":"null"}],"description":"File size in bytes"},"creditCost":{"anyOf":[{"type":"integer","minimum":0,"maximum":9007199254740991},{"type":"null"}],"description":"Parser credits charged for this Contracko Parser file"},"status":{"type":"string","minLength":1,"description":"Item processing status"},"error":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Error message when item processing fails"},"outputPreview":{"description":"Contracko Parser bulk-processing output preview; does not add a contract to the CLM register"},"uploadRetentionExpiresAt":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"description":"ISO-8601 timestamp when uploaded source retention expires"}},"required":["id","fileName","mimeType","fileSize","creditCost","status","error"]},"description":"Per-file parser item status and previews"}},"required":["batch","items"]},"examples":{"success":{"summary":"Batch details returned","value":{"batch":{"id":"62a5e2e7-1b8f-45e0-abed-17f01ba4eb1e","status":"completed","outputFormat":"json","totalFiles":1,"completedFiles":1,"creditCost":1,"retentionExpiresAt":"2026-03-20T10:30:00.000Z","createdAt":"2026-03-13T10:30:00.000Z","metadata":{"customFieldsIncluded":false},"downloadUrl":"https://r2.example.com/exports/62a5e2e7-1b8f-45e0-abed-17f01ba4eb1e.json?X-Amz-Signature=example"},"items":[{"id":"1f818dc2-2211-4df4-8ec1-bfe87b7bc99a","fileName":"vendor-services-agreement.pdf","mimeType":"application/pdf","fileSize":245761,"creditCost":1,"status":"completed","error":null,"outputPreview":{"contractTitle":"Vendor Services Agreement","startDate":"2026-02-01","endDate":"2027-01-31","governingLaw":"California"},"uploadRetentionExpiresAt":"2026-03-14T10:30:00.000Z"}]}}}}}},"400":{"description":"Request validation failed (payload, query, or path format is invalid).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"validation_failed":{"summary":"Invalid input payload","value":{"code":"BAD_REQUEST","message":"Request validation failed","data":{"issues":[{"path":["files",0,"mimeType"],"message":"Invalid MIME type."}]}}}}}}},"401":{"description":"Authentication failed (missing, invalid, revoked, or expired API key).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"missing_api_key":{"summary":"No API key header provided","value":{"code":"UNAUTHORIZED","message":"Missing API key. Send x-contracko-api-key or Authorization: Bearer <key>."}}}}}},"403":{"description":"Access denied because this API key does not include parsing access or the Parsing API is not available for this workspace.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"missing_parsing_access":{"summary":"API key does not include parsing access","value":{"code":"FORBIDDEN","message":"This API key does not have access to this endpoint.","data":{"requiredScopes":["parser:compute"],"availableScopes":["contract:read"]}}},"parsing_unavailable":{"summary":"Parsing API not available","value":{"code":"FORBIDDEN","message":"Parsing API is not available for this workspace."}},"insufficient_credits":{"summary":"Not enough credits available","value":{"code":"FORBIDDEN","message":"Not enough credits available for this request.","data":{"cause":"PARSER_CREDITS_EXHAUSTED","creditsNeeded":2,"creditsRemaining":1}}}}}}},"404":{"description":"The requested parser batch was not found.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"batch_not_found":{"summary":"Parser batch not found","value":{"code":"NOT_FOUND","message":"Parser batch not found."}}}}}},"429":{"description":"Retry later because the request rate limit was reached or too many parser batches are already running for this workspace.","headers":{"Retry-After":{"description":"Number of seconds to wait before retrying the request.","schema":{"type":"string"}},"X-RateLimit-Limit":{"description":"Requests allowed in the current rate-limit window.","schema":{"type":"string"}},"X-RateLimit-Remaining":{"description":"Remaining requests in the current rate-limit window.","schema":{"type":"string"}},"X-RateLimit-Reset":{"description":"Unix timestamp when the current rate-limit window resets.","schema":{"type":"string"}}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"rate_limited":{"summary":"API rate limit reached","value":{"code":"TOO_MANY_REQUESTS","message":"Too many requests. Please try again later."}},"concurrency_limited":{"summary":"Too many parser batches are running","value":{"code":"TOO_MANY_REQUESTS","message":"Too many parser batches are already running for this workspace. Wait for one to finish and try again."}}}}}},"500":{"description":"The server could not complete the request.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiError"},"examples":{"internal_error":{"summary":"Unhandled server error","value":{"code":"INTERNAL_SERVER_ERROR","message":"Unexpected API error"}}}}}}}}}}}